代码说明:
public struct MyStruct
{
public int SomeNumber;
}
public string DoSomethingWithMyStruct(MyStruct s)
{
if (s == null)
return "this can't happen";
else
return "ok";
}
private string DoSomethingWithDateTime(DateTime s)
{
if (s == null)
return "this can't happen"; // XX
else
return "ok";
}
现在,“DoSomethingWithStruct”无法编译:“运算符'=='无法应用于'MyStruct'和'<null>
''类型的操作数。这是有道理的,因为尝试与结构进行参考比较是没有意义的,结构是一种值类型。
OTOH,“DoSomethingWithDateTime”编译,但编译器警告:“检测到无法访问的代码”标记为“XX”的行。现在,我假设这里没有编译器错误,因为DateTime结构重载了“==”运算符。但编译器如何知道代码无法访问?例如它是否在重载“==”运算符的代码中查看? (这是使用Visual Studio 2005以防万一)。
注意:我对上述情况比任何事都更好奇。我通常不会尝试使用“==”来比较结构和空值。
编辑:我会尝试简化我的问题 - 为什么“DoSomethingWithDateTime”会编译,而“DoSomethingWithMyStruct”则没有。两个论点都是结构。
答案 0 :(得分:4)
它知道结构永远不会为空(Nullable<T>
除外);这足以发出警告。
在这个领域有一个已知的编译器问题,它出现在C#2.0编译器和C#3.0编译器之间(目前仍保留在C#4.0编译器中)[我不知道为什么你在VS2005上看到它虽然]。对于使用==
/ !=
运算符的自定义结构,相等性测试不会引发无法访问代码警告。 DateTime
有这些运营商;你的结构没有 - 因此不同。
这个问题是logged on connect,最近由编译器团队进行了研究(他们热衷于在机会出现时修复它)。
答案 1 :(得分:2)
因为DateTime是一个结构,所以它不能为空。并且没有办法以第二个参数为空的方式覆盖结构的==运算符。
答案 2 :(得分:2)
正如Hun1Ahpu所说,它永远不会为空。
但是,您可以提供自己的==运算符,它可以将对象作为参数类型,以允许上述代码进行编译。
显然,你需要它做一些合乎逻辑的事情。