在集合初始化中忘记了“新”声明:这段代码做了什么,为什么要编译?

时间:2015-08-21 18:05:41

标签: c# collections

初始化对象时,我经常编写如下代码:

var myObj = new MyObject
{
    Number = 1,
    ListOfStuff = new List<Stuff>
    {
        new Stuff()
    }
}

但是,有时我会忘记new List<Stuff>,而是写:

var myObj = new MyObject
{
    Number = 1,
    ListOfStuff =
    {
        new Stuff()
    }
}

我不希望这会编译,但确实如此。 ListOfStuff未按照我的预期进行初始化 - 但它是空的。这段代码究竟做了什么?

2 个答案:

答案 0 :(得分:1)

对象初始化语法和集合初始化语法都只是编译器在编译时的语法转换insto赋值和方法调用:

  • 对象初始化语法转换为属性赋值,
  • 集合初始化语法转换为适当的Add方法调用

所以你的代码相当于:

var myObj = new MyObject();
myObj.Number = 1;
myObj.ListOfStuff.Add(new Stuff());

这是一个有效的C#代码,如果MyObject上的默认构造函数初始化ListOfStuff属性,它将起作用。如果没有,它将抛出NullReferenceException

在调用new List()之前,您的代码的第一个版本会明确地将ListOfStuff分配给Add

var myObj = new MyObject();
myObj.Number = 1;
myObj.ListOfStuff = new List<Stuff>();
myObj.ListOfStuff.Add(new Stuff());

答案 1 :(得分:0)

有趣的是,以下初始化ListOfStuff的方法会产生编译错误:

    var myObj = new MyObject();
    myObj.Number = 1;
    myObj.ListOfStuff = 
        {
            new Stuff()
        };
    };