【问题标题】:Null-coalescing operators with operands of different types具有不同类型操作数的空合并运算符
【发布时间】:2020-05-01 06:58:50
【问题描述】:

我知道你不能将不同的类型复合成一个结果,但我不明白为什么会这样。

例如。

Guid? ID;
int ID2;
var ID3 = ID ?? ID2;

上面的代码不管ID的可空性还是ID3、var、object等的类型都不起作用。

谁能解释为什么不允许这样做?

我的实际代码如下所示:

public StandAloneMachine Get(int id, Guid? FKGuid = null, string FKName = "") 
{ 
    var parameters = new Parameters() 
    { 
        new Parameter("id", FKGuid ?? id) 
    }; 
}

【问题讨论】:

标签: c# null-coalescing-operator


【解决方案1】:

有没有人有理由不允许这样做?

这就是语言的设计方式。它应该怎么做?您如何将一个 32 位数字 int 转换为一个由多个数字部分组成的结构 GUID,反之亦然?

这段代码:

var ID3 = ID ?? ID2

翻译成类型意味着(伪代码):

(inferred type_) = Guid? ?? int;

和?? 运算符自然要求其参数的类型兼容。实际规则相当复杂,可以在in the C# language specification here找到。

无论如何,null-coalescing 运算符返回单个值,并且它的左右参数都必须计算为相同类型的值。因此,结果可能是或者一个Guid,或者一个int。 (inferred type) 就是这种类型。但是,?? 无法将Guid 和int 操作数的值转换为单一类型的值。

注意:您可以争辩说编译器可以选择object 作为与Guid 和int 兼容的关闭类型,然后将这些值装箱到一个对象中。但是,这会破坏强类型检查的意义。只是“太放松了”。

在您的特定示例中,坚持使用?? 似乎是人为的;一个好的旧 ?: 和代码中的更多表现力会做得更好,甚至可能有助于提高可读性:

var parameters = new Parameters() 
{ 
    new Parameter("id", FKGuid.HasValue ? ToTypeParameterExpects(FKGuid.Value) : ToTypeParameterExpects(id)) 
}; 

显然,ToTypeParameterExpects 转换为 Parameter 的构造函数期望值的任何类型。

【讨论】:

  • 这就是语言的设计方式从你和 Amy 链接的规范来看,这似乎是事实感谢您对注释的更新
猜你喜欢
  • 1970-01-01
  • 2018-08-29
  • 2017-08-26
  • 2021-08-31
  • 2021-09-25
  • 2017-07-14
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多