2015-10-01 2 views
7

Я только заметил, что возможно следующее в C#, написанной в Visual Studio 2015, но я никогда не видел его раньше:Новый синтаксис инициализатора объекта C# 6?

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, так что, возможно, он всегда был там?

+0

Возможный дубликат (http://stackoverflow.com/questions/32342188/c-sharp- object-initialization-bug) –

ответ

11

Если вы запустите этот код, вы получите исключение NullReferenceException.

Это не будет создавать экземпляр Y, он будет вызывать добытчик X.B собственности и попытаться присвоить значение свойству C.

Он всегда работал так. Согласно спецификации языка C# 5.0:

Инициализатор элемента, который указывает инициализатор объекта после того, как знак равенства является инициализатором вложенного объекта, то есть инициализацией внедренного объекта. Вместо назначения нового значения полю или свойства назначения в инициализаторе вложенных объектов рассматриваются как назначения членам поля или свойства.

+0

Вы правы, спасибо. Таким образом, мы можем изменить объявление 'X.B', чтобы оно выглядело как' public Y B {get; } = new Y(); 'и этот код будет работать, как ожидалось. Странно, что я никогда не замечал этого синтаксиса раньше! – jonnystoten

+2

Эта функция была введена в C# 3.0 – Vova

6

Эта функция была введена в C# 3.0 в качестве инициализаторов объектов.

См. Пример на стр. 169 из C# Language 3.0 specification: [? # Инициализации объекта ошибка C]

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; 
Смежные вопросы