应用operator |时的过载分辨率到不同类型的枚举

时间:2013-01-27 00:11:17

标签: c# enums overload-resolution

在阅读了最近的问题Operations between different enum types are allowed in another enum declaration but not elsewhere后,我想出了这个例子:

    enum Alpha : long
    {
        X,
    }

    enum Beta : ulong
    {
        X,
    }

    enum Gamma : long
    {
        X = Alpha.X | Beta.X,   // problem?
    }

    enum Delta : ulong
    {
        X = Alpha.X | Beta.X,   // no problem?
    }

编译结果:Gamma将无法编译( CS0266:无法将类型'ulong'隐式转换为'long'。存在显式转换(您是否错过了演员?)) 。 Delta愉快地汇编。

这个是不是C#语言规范不能期待的东西?

(注意:如果我将要初始化的Alpha成员更改为负常量,例如-1L,那么GammaDelta都不会编译。)< / p>

2 个答案:

答案 0 :(得分:1)

是的,它是预期的,并不是特定于枚举的东西。您可以将其简化为:

long a = 1L | 1UL; // Cannot implicitly convert type 'ulong' to 'long'. An explicit conversion exists (are you missing a cast?)
ulong b = 1L | 1UL;

C#语言规范中的以下引用描述了它发生的原因。

  

6.1.9隐式常量表达式转换

     

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

     

·可以转换int类型的常量表达式(第7.19节)   输入sbyte,byte,short,ushort,uint或ulong,提供值   constant-expression的值在目标范围内   类型。

     

· long类型的常量表达式可以转换为类型   ulong,只要constant-expression的值不是负数。

     

6.1.2隐式数字转换

     

隐式数字转换为:

     

·从long到float,double或decimal。

     

·从ulong到float,double或decimal。

换句话说,Alpha.X(如果基础值为正)可以(实际上是!)隐式转换为ulong。但是Alpha.X | Beta.X的结果是ulong,根据规范,它不能隐式转换为long

但是,一旦您将要初始化的Alpha.X更改为负常量,例如-1L,那么,根据上面的引用,它不能再隐式转换为ulong并且编译将失败并出现其他错误:Operator '|' cannot be applied to operands of type 'long' and 'ulong'

答案 1 :(得分:0)

是的,没有预期的,没有从ulong到任何整数类型的隐式转换。

一旦你告诉编译器你很长的是-ve,你给它足够的信息说,你不想这样做。

就个人而言,我很高兴它会因为长时间而感到不安ulong,但毫无疑问,一些C程序员影响了这个决定。 :(