2009-08-07 10 views
9

と仮定私は文字列のコレクションがあります。生成カンマ区切り

"foo" 
"bar" 
"xyz" 

をそして私のようなものの中に、リストからカンマ区切り値を生成したいと思います:

"foo, bar, xyz" 

お知らせの欠如"、 " 最後に。

  • 用のループとString.Formatの()またはのStringBuilder:

    は、私はこれを生成する方法の数十があることを認識しています。 > 0

  • 値は入れていない場合
  • 利用の整数カウンタとエンディングを削除する「 『』、」最初の実行上の
  • など

私は右の持っているもののサンプルコード現在:

if (strs.Count() > 0) 
{ 
    var sb = new StringBuilder(); 
    foreach (var str in strs) 
    sb.AppendFormat("{0}, ", str); 
    return sb.Remove(0, 2).ToString(); 
} 

上記のシナリオで再利用可能なコードは何ですか?その理由は何ですか?

答えて

4

String.Joinが正しい答えですが、IEnumerableをする場合には、LINQのは、多くの場合、forループよりも短くなっている。

someStringCollection.Aggregate((first, second) => first + ", " + second); 
+0

LINQの使い方 –

26

この目的のためにBCLに存在するstring.Joinメソッドを使用します。

例:

var myArray = new string[] { "one", "two", "three" }; 
var output = string.Join(", ", myArray); 

それとも、.NET 3.5を使用している場合は、次のような任意のIEnumerable<string>でこれを行うことができます。

var output = string.Join(", ", myEnumerable.ToArray()); 

(これが最善を与えないことに注意してくださいそれは明らかに依然として「O(n)」であり、ほぼすべての場合に適しているはずです)。

あなたの列挙型がタイプstring(一般にIEnumerable<T>)でない場合は、Selectメソッドを使用して結果を文字列に変換することができます。

var output = string.Join(", ", myEnumerable.Select(e => e.ToString()).ToArray()); 

私はあなたが値を扱っている場合は、潜在的に自分自身にカンマが含まれているかもしれないわからないんだけど、これも同様に、引用符(")で囲むと、引用符をエスケープすることで回避することができますCSV形式に変換します。

var output = string.Join(", ", items.Select(x => x.Contains(",") ? 
    "\"" + x.Replace("\"", "\"\"") + "\"" : x); 

もちろん、それらをもう一度元に戻すことは、ややトリシアーな作業ですが、これには少しの正規表現が必要です。

+1

うーん...私はこの機能が存在しないことを知っていた(私の質問が悪くなる)。 –

+0

@Adrian:心配はいりません。 .NETのバックグラウンドではない場合、フレームワーク内の新しいものを発見することは必ずしも容易ではありません。これは、親しみを育てるという重大なプロセスです。 – Noldorin

+1

それは問題です。私は最初のバージョンから.NETをやっています。ダー。 –

2

使用

string s = string.Join (",", new string[] {"aaa", "bbb", "ccc"}); 
3
string finalstr = String.Join(",", strs); 
0

あなたは文字列の配列を持っている場合は、Noldorinのソリューションで行きます。

しかし、それはいくつかの他のコレクション型だならば、私はこれを行う可能性があります:他の人が言っている

if (strs.Count() > 0) 
{ 
    var sb = new StringBuilder(); 
    foreach (var str in strs) 
    sb.AppendFormat("{0} {1}", (0 == sb.Length ? "" : ","), str); 
    return sb.ToString(); 
} 
4

通り:String.Joinは、これを行うための最善の方法通常です。しかし、配列ではなくIEnumerableを持っていればどうでしょうか?おそらく、遅延実行を使用してファイルからそれらを読み取るときに、これらを列挙するコードがあります。この場合、String.Joinは、配列を作成するために1回、それに1回追加するために、2回、文字列を2回ループする必要があるため、あまりうまくいきません。

public static string ToDelimitedString(this IEnumerable<string> source, string delimiter) 
{ 
    string d = ""; 
    var result = new StringBuilder(); 

    foreach(string s in source) 
    { 
     result.Append(d).Append(s); 
     d = delimiter; 
    } 
    return result.ToString(); 
} 

これはほとんどだけでなく、String.Join を実行し、より一般的なケースで動作します。その場合は、あなたがより多くのこのような何かをしたいです。次に、文字列配列または任意の他のIEnumerableを与え、あなたはこのようにそれを呼び出すことができます。

string finalStr = MyStrings.ToDelimitedString(","); 
+0

はい、それは明らかにもっと一般的なシナリオです。 IEnumerable はstring []よりも優先されます。 –

+0

+1 'result.Append(d).Append(s)'は面白いです...それも考えたことはありません。この単純な作業が現在どのように多くの異なる方法で行われているかを知るのはちょっとしたことです。 –

+0

本当にクールなことは、ジッタが余計な割り当てを通常は最適化するため、コードはあなたが望むものを正確に実行するということです。 –

関連する問題