三元运算符行为不一致

Meh*_*lak 51 c# int casting short conditional-operator

以下表达式是可以的

short d = ("obj" == "obj" ) ? 1 : 2;
Run Code Online (Sandbox Code Playgroud)

但是当您像下面一样使用它时,会发生语法错误

short d = (DateTime.Now == DateTime.Now) ? 1 : 2;
Run Code Online (Sandbox Code Playgroud)

无法将类型'int'隐式转换为'short'.存在显式转换(您是否错过了演员?)

任何人都可以解释为什么会这样吗?

在三元运算符中比较字符串到字符串和datetime到datetime之间有区别吗,为什么?

如果你能帮助我,我将不胜感激.

Dam*_*ver 59

C#语言规范,第5版,第6.1.9节:

隐式常量表达式转换允许以下转换:

  • 如果constant-expression的值在目标类型的范围内,则int类型的常量表达式(第7.19节)可以转换为sbyte,byte,short,ushort,uint或ulong类型.

您的第一个示例常量表达式,因为它可以在编译时进行计算.但有关详细信息,请参阅第7.19节:

在常量表达式中只允许以下构造:

  • 文字(包括空文字).

[...]

  • 预定义的+, - ,*,/,%,<<,>>,&,|,^,&&,||,==,!=,<,>,<=和> =二元运算符,每个都提供操作数是上面列出的类型.
  • ?:条件运算符.

  • @Joker_vD:如果您的问题"为什么字符串特殊?" 答案是没有修辞的:字符串是特殊的,因为"32位int"是特殊的:因为将这些常用数据类型的支持直接添加到语言中是非常实用的**.对于数据类型的处理,C#并不是为了民主/不可知/使力平衡/无论如何.实际上人们在LOB应用程序中使用的数据类型是特殊的,因为使它们变得特殊是务实的. (9认同)
  • @Joker_vD - 小心解释你的推理?为什么string*literals*应该与任何其他文字区别对待? (8认同)

Jak*_*cki 17

我相信在第一种情况下,编译器知道字符串在编译时是相等的,因此将代码优化为:

short d = 1;

这是有效的,因为1可以分配给short变量.

在第二种情况下,优化不会发生,因为编译器无法在编译时推断出相等性,因此它会离开:

short d = (DateTime.Now == DateTime.Now) ? (long)1 : (long)2;

这将编译:

short d = (DateTime.Now == DateTime.Now) ? (short)1 : (short)2;

IL(LinqPad)呼叫短路d =("obj"=="obj")?1:2; :

IL_0001:  ldc.i4.1    
IL_0002:  stloc.0     // d
Run Code Online (Sandbox Code Playgroud)