0

複数のデータベース列のセミコロン区切りのリストを作成するためのより効率的な方法を探しています。私が現在使用しているコードは次のようになります(そしてそれは機能します):

//Process List of things
var things = DB.DbColumn_1.HasValue ? DB.DbColumn_1.Value.Equals(true) ? "thing 1;" : "" : "");
things += DB.DbColumn_2.HasValue ? DB.DbColumn_2.Value.Equals(true) ? "thing 2;" : "" : "");
things += DB.DbColumn_3.HasValue ? DB.DbColumn_3.Value.Equals(true) ? "thing 3;" : "" : "");
things += DB.DbColumn_4.HasValue ? DB.DbColumn_4.Value.Equals(true) ? "thing 4;" : "" : "");
// Remove final ';' from thing list if non-empty
things = things.Length > 0 ? things.Substring(0, things.Length-1) : things;

私は実際に処理する約8つの列を持っています-例はあなたにそのいくつかを省きます。だから私は単純な文字列を構築するための大きな醜いコードブロックを持っています。これは問題なく機能しているように見えますが、私がやろうとしていることにはコードが多すぎるようです。また、この状況で「.Equals()」を使用する場合は注意が必要ですか?

ブレーンストーミングを行った後、文字列自体を作成するための別の関数を作成するなど、これよりも効率的と思われるものは何もありませんでした。すべての列は一意のnull許容boolであり、結果のリストに対して一意の文字列出力があります。

または、これらの要素に十分に効率的にアクセスして、心配する必要はありませんか?

ありがとうございました!

4

3 に答える 3

2

DB.DbColumn_1.HasValue && DB.DbColumn_1.Value.Equals(true)非常に難しい書き方ですDB.DbColumn_1.GetValueOrDefault()が、機能的には同等です。http://msdn.microsoft.com/en-us/library/1t3y8s4s(v=vs.80).aspxおよびhttp:Nullable<T>で、構造体(DB列のタイプであるとbool?同等)の詳細を参照してください。 //msdn.microsoft.com/en-us/library/b3h38hb0.aspxNullable<bool>

次のいずれかのアプローチを使用できます。

var sections = new List<string>();
if (DB.DbColumn_1.GetValueOrDefault()) sections.Add("thing 1");
if (DB.DbColumn_2.GetValueOrDefault()) sections.Add("thing 2");
//...other columns
var things = string.Join(";", sections);

または:

var pairs = new List<Tuple<bool?, string>>
{
    Tuple.Create(DB.DbColumn_1, "thing 1"),
    Tuple.Create(DB.DbColumn_2, "thing 2")
    //...other columns
};
var things = string.Join(";", pairs.Where(x => x.Item1.GetValueOrDefault()).Select(x => x.Item2));

pairsまたは、一度だけ設定します。

static readonly List<Tuple<Func<DBType, bool?>, string>> pairs = new List<Tuple<Func<DBType, bool?>, string>>
    {
        new Tuple<Func<DBType, bool?>, string>(d => d.DbColumn_1, "thing 1"),
        new Tuple<Func<DBType, bool?>, string>(d => d.DbColumn_2, "thing 2")
        //...other columns
    };

void inSomeMethod()
{
    var things = string.Join(";", pairs.Where(x => x.Item1(DB).GetValueOrDefault()).Select(x => x.Item2));
}

もちろん状況にもよりますが、最後のものが一番好きです。宣言の冗長性がpairs気になる場合(つまり繰り返すTuple<Func<DBType, bool?>, string>)、これを行うことができます:

class ReadDbBools : Tuple<Func<DBType, bool?>, string>
{
    public ReadDbBools(Func<DBType, bool?> retrieveFunc, string ifTrue) : base(retrieveFunc, ifTrue) { }
}

static readonly List<ReadDbBools> pairs = new List<ReadDbBools>
{
    new ReadDbBools(d => d.DbColumn_1, "thing 1"),
    new ReadDbBools(d => d.DbColumn_2, "thing 2")
    //...other columns
};
于 2012-05-03T14:47:29.610 に答える
0

linq-to-sqlモデルを少し拡張して、期待する値を返すことができるので、その部分は邪魔になりません。

public partial class Entity {
    public string DbColumn_1_Display {
        return (DbColumn_1 ?? false) ? "thing_1" : "";
    }
    /*for each property*/
}

そしてそれを選択するためにあなたはこのようなことをすることができます:

var result = from db in DB
             select new { 
                   c1 = DbColumn_1_Display,  
                   c2 = DbColumn_2_Display /*etc*/};
var string = string.Format("{0};{1};{2}/*...*/", result.c1, result.c2 /*...*/);

これが物事を容易にするかどうかわからない。

于 2012-05-03T14:45:06.387 に答える
0

null許容型から始めると、Equalsメソッドをオーバーライドするので、これの代わりに

DB.DbColumn_1.HasValue ? DB.DbColumn_1.Value.Equals(true) ? "thing 1;" : "" : ""

あなたはこれを書くことができます

DB.DbColumn_1.Equals(true) ? "thing1;" : ""

またstring.Join、最後に余分なセミコロンを処理するための非常に優れた方法を使用すると、次のようになります。

var things = string.Join(";", new []
    {
        DB.DbColumn_1.Equals(true) ? "thing1" : null,
        DB.DbColumn_2.Equals(true) ? "thing2" : null,
        // etc...
    }.Where(i => i != null));

これによりコードが読みやすくなりますが、この処理はとにかくすでにかなり高速であるはずなので、パフォーマンスを向上させるために実際にはあまり効果がありません。

于 2012-05-03T14:48:07.653 に答える