【问题标题】:If the left operand to the ?? operator is not null, does the right operand get evaluated?如果左操作数到 ??运算符不为空,是否评估正确的操作数?
【发布时间】:2014-11-19 09:14:41
【问题描述】:

我正在考虑在 C# 中使用 ?? 运算符(null-coalescing 运算符)。但是 MSDN 上的documentation 是有限的。

我的问题:如果左边的操作数不为空,右边的操作数会被计算吗?

【问题讨论】:

  • 自己试试吧:string s = "A"; Console.WriteLine("Hello" ?? a.Substring(10));

标签: c# .net operators


【解决方案1】:

与以往一样,C# 规范是此类事情的最佳选择。

来自C# 5 specification(强调我的)的第 7.13 节:

a ?? b 形式的空合并表达式要求 a 为可空类型或引用类型。如果a不为null,则a ?? b的结果为a;否则,结果为b仅当a 为空时,该操作才会评估b

关于何时执行任何转换以及确切的行为有更多详细信息,但这是您提出问题的重点。还值得注意的是,空合并运算符是右关联的,所以 a ?? b ?? c 被评估为 a ?? (b ?? c)... 这意味着它只会评估 c 如果 both ab 为空。

【讨论】:

  • 感谢从未想过要检查规格
  • @AntarrByrd:总是检查规范 :) C# 规范是我见过的最好的编写规范之一,它是这类事情的权威来源。
  • 此运算符的关联性实际上对其行为有任何可观察到的影响吗?我正在尝试考虑(a ?? b) ?? c 的行为与a ?? (b ?? c) 不同的情况,但我想不出一个。
  • @JLRishe:如果abc 具有不同的类型,并且该语言最终执行从一种类型到另一种类型的转换,则会产生影响。我曾经有一个例子,但我没有现成的。
  • @JonSkeet 我明白了。谢谢!
【解决方案2】:

来自规范:

a ?? 形式的空合并表达式b 要求 a 是可空类型或引用类型。如果 a 不为空,则 a ?? 的结果b是a;否则,结果为 b。 仅当 a 为空时,该操作才计算 b。

(已添加重点)

【讨论】:

    【解决方案3】:

    看看这个。如果 name 不为 null,则控制台显示“MyName”。如果为空,控制台显示“Called”,然后显示“Allo”

    using System;           
    public class Program
    {
        public static void Main()
        {
            string name = "MyName";
    
            Console.WriteLine(name??test());
        }
    
        private static string test()
        {
            Console.WriteLine("Called");
            return "Allo";
        }
    }
    

    【讨论】:

      【解决方案4】:

      为什么不测试它:)

      void Main()
      {
          var leftOrRight = left ?? right;
      }
      
      public bool? left 
      {
          get
          {
              Console.WriteLine ("Left hit");
              return true;
          }
      }
      
      public bool right 
      {
          get
          {
              Console.WriteLine ("Right hit");
              return true;
          }   
      }
      

      问题的答案是no...第二个值没有得到评估

      【讨论】:

        猜你喜欢
        • 2020-11-19
        • 1970-01-01
        • 2021-09-28
        • 1970-01-01
        • 1970-01-01
        • 2016-12-27
        • 2021-09-25
        • 2011-12-08
        • 2023-04-11
        相关资源
        最近更新 更多