代码之家  ›  专栏  ›  技术社区  ›  Moe Sisko

C 35;“=”运算符:具有不同结构的编译器行为

  •  7
  • Moe Sisko  · 技术社区  · 15 年前

    说明代码:

        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”编译失败:“operator”='不能应用于'mystruct'和' <null> “。这是有意义的,因为尝试将引用与值类型struct进行比较是没有意义的。

    otoh,“doSomethingWithDateTime”编译,但编译器警告:“检测到无法访问的代码”,位于标记为“xx”的行。现在,我假设这里没有编译器错误,因为datetime结构重载了“==”运算符。但是编译器如何知道代码是不可访问的呢?例如,它是否在重载“==”运算符的代码中查找?(这是使用visual studio 2005,以防发生变化)。

    注:我对以上的一切都很好奇。我通常不尝试使用“==”来比较结构和空值。

    编辑:我会尽量简化我的问题-为什么“dosomethingwithdatetime”要编译,而“dosomethingwithmystruct”不编译。两个参数都是结构。

    3 回复  |  直到 15 年前
        1
  •  4
  •   Marc Gravell    15 年前

    它知道结构永远不为空( Nullable<T> 旁白);这足以发出警告。

    这方面有一个已知的编译器问题,它出现在C 2.0编译器和C 3.0编译器之间(目前仍在C 4.0编译器中)[不过,我不确定为什么您在VS2005上看到它]。相等测试不会对具有 == / != 运算符。 DateTime 有这些运算符;您的结构没有-因此有所不同。

    这个问题是 logged on connect ,最近编译器团队(他们非常希望在出现机会时修复它)已经对此进行了研究。

        2
  •  2
  •   leppie    15 年前

    正如hun1ahpu所说,它永远不能为空。

    但是,您可以提供自己的==运算符,该运算符可以将对象作为允许编译上述代码的参数类型。

    显然,你需要它来做一些合乎逻辑的事情。

        3
  •  2
  •   Hun1Ahpu    15 年前

    因为datetime是一个结构,所以不能为空。而且无法重写结构的==运算符,这样第二个参数将为空。

    推荐文章