web-dev-qa-db-ja.com

なぜString.Formatを使うのですか?

連結演算子(VBではString.Format、C#では&)とは対照的に、誰もがC#およびVB .NETで+を使用するのはなぜですか

主な違いは何ですか?なぜ誰もがString.Formatの使用にそれほど興味を持っているのですか?私はとても興味があります。

いくつかの理由が考えられます。

読みやすさ

string s = string.Format("Hey, {0} it is the {1}st day of {2}.  I feel {3}!", _name, _day, _month, _feeling);

vs:

string s = "Hey," + _name + " it is the " + _day + "st day of " + _month + ".  I feel " + feeling + "!";

フォーマット指定子(これにはカスタムフォーマッタを書くことができるという事実も含まれます)

string s = string.Format("Invoice number: {0:0000}", _invoiceNum);

vs:

string s = "Invoice Number = " + ("0000" + _invoiceNum).Substr(..... /*can't even be bothered to type it*/)

String Template Persistence

データベースに文字列テンプレートを保存したい場合はどうすればいいですか?文字列フォーマットの場合

_id         _translation
  1         Welcome {0} to {1}.  Today is {2}.
  2         You have {0} products in your basket.
  3         Thank-you for your order.  Your {0} will arrive in {1} working days.

vs:

_id         _translation
  1         Welcome
  2         to
  3         .  Today is
  4         . 
  5         You have
  6         products in your basket.
  7         Someone
  8         just shoot
  9         the developer.
391
Moo-Juice

もう少し読みやすく、数人の演算子を追加するだけでなく、アプリケーションが国際化されている場合にも便利です。多くの場合、変数は数字やキーワードであり、言語によって順序が異なります。 String.Formatを使用することで、さまざまな文字列がリソースファイルに格納されてもコードを変更しないでおくことができます。そのため、コードは最終的には

String.Format(resource.GetString("MyResourceString"), str1, str2, str3);

あなたのリソース文字列は

英語:"blah blah {0} blah blah {1} blah {2}"

ロシア語:"{0} blet blet blet {2} blet {1}"

ロシアでは事態への対処方法について異なる規則があるため、順序が異なる、または文の構造が異なる場合があります。

90
doobop

まず、見つけます

string s = String.Format(
    "Your order {0} will be delivered on {1:yyyy-MM-dd}. Your total cost is {2:C}.",
    orderNumber,
    orderDeliveryDate,
    orderCost
);

読み、書きそして保守がずっと簡単

string s = "Your order " +
           orderNumber.ToString() +
           " will be delivered on " +
           orderDeliveryDate.ToString("yyyy-MM-dd") +
           "." +
           "Your total cost is " +
           orderCost.ToString("C") + 
           ".";

以下がどれほど保守的であるかを見てください。

string s = String.Format(
    "Year = {0:yyyy}, Month = {0:MM}, Day = {0:dd}",
    date
);

代わりにdateを3回繰り返さなければならない場合があります。

第二に、String.Formatが提供するフォーマット指定子は、単純な古い連結を使うよりも読みやすく、書きやすく、そして保守しやすい方法で文字列の出力に対して大きな柔軟性を与えます。さらに、String.Formatを使用すると、文化に関する懸念をより簡単に把握できます。

第三に、パフォーマンスが重要な場合、String.Formatが連結よりも優れています。舞台裏ではStringBuilderを使い、 Schlemiel the Painter問題 を避けています。

26
jason

いくつかの理由:

  1. String.Format()は非常に強力です。フォーマット文字列の中で単純なフォーマットインジケータ(固定幅、通貨、文字長など)を使用できます。列挙型の拡張、特定の入力のより複雑な出力へのマッピング、ローカライズなどの目的で、独自のフォーマットプロバイダを作成することもできます。
  2. フォーマット文字列を設定ファイルに入れることで、いくつかの強力なことができます。
  3. String.Format()は、背後でStringBuilderと効率的なステートマシンを使用するため、多くの場合は高速ですが、.Netでの文字列連結は比較的低速です。小さい文字列の場合、その違いはごくわずかですが、文字列のサイズと置換される値の数が増えるにつれて顕著になることがあります。
  4. String.Format()は実際には多くのプログラマー、特に古いCのprintf()関数の変種を使っているバックグラウンドから来たプログラマーにとってなじみがあります。

最後に、StringBuilder.AppendFormat()を忘れないでください。 String.Format()は実際にはこのメソッドを使用しています*ので、StringBuilderに直接アクセスすると一種のハイブリッドなアプローチになります。大きな文字列の一部には明示的に.Append()を使い、その他は.AppendFormat()を使います。


* [編集]元の答えは8歳になりました、そして私は以来、文字列補間が.Netに追加されたときにこれが変わったかもしれないという徴候を見ました。しかし、私はまだ変更を確認するために参照元に戻っていません。

17
Joel Coehoorn

String.Format は、文字列に追加される各項目の特定のフォーマットを指定する機能など、連結演算子に加えて多くのオプションを追加します。

可能なことの詳細については、MSDNの「 Composite Formatting 」というセクションを読むことをお勧めします。通常の連結演算子に対するString.Format(およびxxx.WriteLineおよびその他の複合フォーマットをサポートするメソッド)の利点について説明します。

5
Reed Copsey

パフォーマンスの側面に関する興味深い点が この質問 にあります

ただし、読みやすさのためにパフォーマンスが重要でない限り、個人的にはstring.Formatをお勧めします。

string.Format("{0}: {1}", key, value);

より読みやすいです

key + ": " + value

例えば。また、懸念のニースの分離を提供します。あなたが持つことができるという意味

string.Format(GetConfigValue("KeyValueFormat"), key, value);

そして、キー値のフォーマットを"{0}: {1}"から"{0} - {1}"に変更すると、コードが変更されるのではなく設定が変更されます。

string.Formatには、一連のフォーマット規定、整数、日付フォーマットなども組み込まれています。

4
SamStephens

'string +"Value"+ string'のように文字列を書くのが好ましくない理由の1つは、ローカライズのためです。ローカライズが行われている場合は、ローカライズされた文字列を正しくフォーマットする必要があります。これは、コーディングされている言語とは大きく異なる場合があります。

たとえば、異なる言語で次のエラーを表示する必要があります。

MessageBox.Show(String.Format(ErrorManager.GetError("PIDV001").Description, proposalvalue.ProposalSource)

どこで

'ErrorCollector.GetError("ERR001").ErrorDescription'"Your ID {0} is not valid"のような文字列を返します。このメッセージは多くの言語にローカライズする必要があります。その場合、C#では+を使用できません。 string.formatに従う必要があります。

2
user2186941