新的 C# 6 对象初始值设定项语法?

New C# 6 object initializer syntax?

我刚刚注意到在Visual Studio 2015 年写的 C# 中可能有以下内容,但我以前从未见过:

public class X
{
    public int A { get; set; }

    public Y B { get; set; }
}

public class Y
{
    public int C {get; set; }
}

public void Foo()
{
    var x = new X { A = 1, B = { C = 3 } };
}

我的期望是 Foo 必须像这样实现:

public void Foo()
{
    var x = new X { A = 1, B = new Y { C = 3 } };
}

注意不需要调用new Y

这是 C# 6 中的新功能吗?我在 release notes 中没有看到任何提及此内容,所以它可能一直存在?

如果您 运行 此代码,您将得到 NullReferenceException。

它不会创建Y的实例,它会调用X.B属性的getter并尝试给属性赋值C .

它总是那样工作。根据 C# 5.0 语言规范:

A member initializer that specifies an object initializer after the equals sign is a nested object initializer, i.e. an initialization of an embedded object. Instead of assigning a new value to the field or property, the assignments in the nested object initializer are treated as assignments to members of the field or property.

此功能是在 C# 3.0 中作为对象初始值设定项引入的。

参见第 1 页的示例。 C# Language 3.0 specification 的 169:

Rectangle r = new Rectangle {
    P1 = { X = 0, Y = 1 },
    P2 = { X = 2, Y = 3 }
};

效果相同
Rectangle __r = new Rectangle();
__r.P1.X = 0;
__r.P1.Y = 1;
__r.P2.X = 2;
__r.P2.Y = 3;
Rectangle r = __r;