このコードは無効です:
private void Foo(string optionalString = string.Empty)
{
// do foo.
}
しかし、このコードは:
private void Foo(string optionalString = "")
{
// do foo.
}
どうして? string.Emptyは定数ではなく読み取り専用フィールドであるため、オプションのパラメーターのデフォルトはコンパイル時の定数でなければなりません。
だから、私の質問に...(まあ、心配)
これは私がしなければならなかったことです:
private const string emptyString = "";
private void Foo(string optionalString = emptyString)
{
// do foo.
if (!string.IsNullOrEmpty(optionalString))
// etc
}
オプションの文字列パラメーターをどのように処理しますか?
String.Empty をコンパイル時の定数にできないのはなぜですか?
うーん...文字列optionalParm = ""の何が問題になっていますか?なぜそれが悪いのですか?この場合、空の文字列のシンボリック定数が本当に必要だと思いますか?これはどうですか?
const int Zero = 0;
void SomeMethod(int optional = Zero) { }
それはあなたにはまったくばかげているように見えますか?
""値が気に入らない場合は、default(string)を使用できます。
私はそれで遊んで、それは許可されています。
private static void foo(string param = default(string)) {
if (!string.IsNullOrEmpty(param)) // or param != default(string)
Console.WriteLine(param);
}
コード分析警告1026 は、オプションのパラメーターを使用しないことを示しています。次のように、オーバーロードメソッドを使用することをお勧めします。
private void Foo()
{
Foo(string.Empty);
}
private void Foo(string optionalString)
{
// do foo.
if (!string.IsNullOrEmpty(optionalString))
// etc
}
それらを処理する最良の方法は、
private void Foo(string optionalString = "")
{
// do foo.
}
したがって、String.Emptyは使用できません。誰もが「」を認識しますが、もし私が見つけたらoptionalString = nullString
どうすればよいかわからない。 それ以外の場合は、モノにemptyString
--それはnullではありません!
私はこの質問に答えています。
Why can they not make String.Empty a compile-time constant?
Mscorlib.dllのString.csのリフレクターを介した逆アセンブルコードを以下に示します。
public static readonly Empty;
static String()
{
Empty = "";
WhitespaceChars = new char[] {
'\t', '\n', '\v', '\f', '\r', ' ', '\x0085', '\x00a0', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',
' ', ' ', ' ', ' ', '', '\u2028', '\u2029', ' ', ''
};
}
したがって、Windowsプラットフォームでは、string.Emptyは正確に ""です。しかし、ご存知ですか、MartianのOSでは、EmptyとWhitespaceCharsの定義が異なります。
Null、 ""、および空白文字を同じように失って処理しても構わない場合は、デフォルトでnull
を使用できます。これは、dbへの信頼できる接続の可能性があるため、ユーザー名とパスワードがオプションのフィールドである場合に非常に便利です。このロジックを変更して、文字列をnull
にリセットし、アサートとif
を変更できます。重要な部分は、一貫した規則を持つことです。
private void RunSql(string serverName, string databaseName, string userName = null, string password = null)
{
userName = Strip(userName);
password = Strip(password);
// The `MsTest` assert - works in both `Debug` and `Release` modes.
Assert.AreEqual<bool>(
userName == String.Empty,
password == String.Empty,
"User name and password should be either both empty or both non-empty!");
Assert.IsFalse(String.IsNullOrWhiteSpace(serverName));
Assert.IsFalse(String.IsNullOrWhiteSpace(databaseName));
var cmdBuilder = new StringBuilder();
cmdBuilder.AppendFormat("sqlcmd -E -S {0} -d {1} ", serverName, databaseName);
if (userName.Length > 0)
{
cmdBuilder.AppendFormat("-U {0} -P {1} ", userName, password);
}
// Complete the command string.
// Run the executable.
}
// Cannot think of a good name. Emptify? MakeNullIfEmpty?
private string Strip(string source)
{
if (String.IsNullOrWhiteSpace(source))
{
return String.Empty;
}
return source;
}