【问题标题】:Strange behavior of the '??'-operator in C# 3.5C# 3.5 中 '??' 运算符的奇怪行为
【发布时间】:2012-02-07 01:19:48
【问题描述】:

这是一个错误还是我解释 '??' - 运算符错误?查看下面的 get 属性和 cmets。

我正在使用 C# .NET 3.5

    private List<MyType> _myTypeList;

    private List<MyType> MyTypeList
    {
        get
        {
            //The two code lines below should each behave as the three under, but they don't?
            //The ones uncommented are working, the commented result in my list always returning empty (newly created I suppose).

            //return _myTypeList ?? new List<MyType>();
            //return _myTypeList == null ? new List<MyType>() : _myTypeList;

            if (_myTypeList == null)
                _myTypeList = new List<MyType>();
            return _myTypeList;
        }
    }

编辑:对于刚提出这个问题时看到这个问题的每个人表示抱歉,其中的一些错误让每个人都感到困惑。

感谢所有出色而快速的反馈!我现在已经理解我犯的错误了。 谢谢!

【问题讨论】:

  • 我在您的代码示例中看不到 ?? 的使用。

标签: c# .net-3.5 null-coalescing-operator


【解决方案1】:

您演示的代码不使用 ??运算符(合并运算符)。相反,您使用的是三元运算符。

试试

return _myTypeList ?? ( _myTypeList = new List<MyType>() );

改为。

看看这个:

        static void Main( string[] args )
        {
            var x = GetList ();

            if( _theList == null )
            {
                Console.WriteLine ("_theList is null");
            }
            else
            {
                Console.WriteLine ("_theList has been initialized.");
            }
            Console.ReadLine ();
        }

        private static List<int> _theList;

        public static List<int> GetList()
        {
            return _theList ?? ( _theList = new List<int> () );
        }

上面的代码会输出'_theList has been initialized'。

您的评论行:

//return _myTypeList == null ? new List<MyType>() : _myTypeList;

永远不会像您期望的那样工作,因为您没有(懒惰)在任何地方初始化 _myTypeList。
_myTypeList == null 将始终评估为 true,因为 _mytypeList 从未初始化,因此,您将始终返回新的 List 实例。

【讨论】:

  • 抱歉,我的问题写得太快了。现在已经编辑了。你只是为了快;)
  • 不是在我输入答案时。 :)
【解决方案2】:

这一行:

return _myTypeList == null ? new List<MyType>() : _myTypeList;

相当于:

    if (_myTypeList == null)
        return new List<MyType>();
    return _myTypeList;

不要:

    if (_myTypeList == null)
        _myTypeList = new List<MyType>();
    return _myTypeList;

你后来添加的??的版本太难读了,我就不分析了。让我们先获取?

【讨论】:

  • 这两个代码sn-ps的语义没有区别吧?
  • @IgorKorkhov 有。在第一种情况下,如果 _myTypeList 最初为 null,则它仍然为 null。
  • Darrans:抱歉,你当然是对的,我只是忽略了 _myTypeList 不是局部变量这一事实。
【解决方案3】:

版本 A:

return _myTypeList ?? (_myTypeList = new List<MyType>()); 

B 版:

return _myTypeList == null ? new List<MyType>() : _myTypeList; 

C 版:

if (_myTypeList == null) 
    _myTypeList = new List<MyType>(); 
return _myTypeList; 

A 和 C 的行为应该相同。 B 不应该——它没有将_myTypeList 设置为新列表,它只返回一个。您可以使用在版本 A 中使用的相同语法使其等效:

return _myTypeList == null ? _myTypeList = new List<MyType>() : _myTypeList; 

【讨论】:

    【解决方案4】:

    如果您必须使用??,请使用它

    _myTypeList = _myTypeList ??  new List<MyType>();
    return  _myTypeList;
    

    但一个简单的 if 也可以

    【讨论】:

      【解决方案5】:

      当你使用语法时

      return _myTypeList == null ? new List<MyType>() : _myTypeList;
      

      如果 _myTypeList 为空,则返回 List() 类型的新 MyType 列表。但是 _myTypeList 仍然为空。你没有初始化它。

      而在第二种情况下,您实际上是初始化 _myTypeList 然后返回它。

      【讨论】:

        【解决方案6】:

        ?? 运算符的意思是:如果左边的操作数不是null,则运算的结果是左边的操作数。否则,操作的结果是右手操作数。即:

        foo = bar ?? frob
        

        如果bar != null,则为foo = bar,否则为foo = frob

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2012-02-29
          • 1970-01-01
          • 2012-01-22
          • 1970-01-01
          • 2013-10-29
          相关资源
          最近更新 更多