2016-11-17 21 views
15

o zaman kalan diyelim BarPropertyInA başlatılıyor sözdizimi beni kelimeler Tanınmayan C# sözdizimi

public static void Main(string[] args) 
{ 
    var foo = new Foo 
    { 
     IntPropertyInFoo = 123, 
     BarPropertyInA = // Ommiting new and type name - why does it compile? 
     { 
      StringPropertyInBar = "something" 
     } 
    }; 
} 

, kod derlemesinin çünkü uyarılar olmadan ve çalıştırıldığında, NullReferenceException atar. Bu sözdizimini tanımıyorum, ancak bir özellik yerine bir alanla kullanıldığında aynı etkiye sahip gibi görünüyor. benziyor

.method public hidebysig static void Main(string[] args) cil managed 
{ 
    .entrypoint 
    // Code size  34 (0x22) 
    .maxstack 3 
    .locals init ([0] class Test.Foo foo) 
    IL_0000: nop 
    IL_0001: newobj  instance void Test.Foo::.ctor() 
    IL_0006: dup 
    IL_0007: ldc.i4.s 123 
    IL_0009: callvirt instance void Test.Foo::set_IntPropertyInFoo(int32) 
    IL_000e: nop 
    IL_000f: dup 
    IL_0010: callvirt instance class Test.Bar Test.Foo::get_BarPropertyInA() 
    IL_0015: ldstr  "something" 
    IL_001a: callvirt instance void Test.Bar::set_StringPropertyInBar(string) 
    IL_001f: nop 
    IL_0020: stloc.0 
    IL_0021: ret 
} // end of method Program::Main 

: derlenmiş kod Disassembling

bu verir

public static void Main(string[] args) 
{ 
    var foo = new Foo 
    { 
     IntPropertyInFoo = 123 
    }; 

    foo.BarPropertyInA.StringPropertyInBar = "something"; 
} 

Yani bu tesisin/alanın üyelerini başlatılıyor için bazı sözdizimsel şeker olması gerekiyordu olduğunu koşuluyla özellik/alan kurucuda başlatıldı?

+0

Bu yüzden, sınıf kurucumdaki diğer sınıfları ve listeleri her zaman yeni ekledim. – Gavin

+1

Eğer 'BarPropertyInA' yeni bir 'Bar' olarak ayarlayan 'Foo' için bir kurucu vardı, o zaman bu sadece 'StringPropertyInBar' özelliğini ayarlamanızı sağlar. Bunun yerine "BarPropertyInA.StringPropertyInBar =" birşeyler " – juharr

+0

" gibi bir şeyle gittiler. Aynısını dizinin yapıcıları ve benzerleri ile yaptım. .Net, – maximdumont

cevap

2

Evet, boş değil, boş olarak başlayan özellikleri başlatmak için kullanılan bir tür kısa yoldur. Net koleksiyon özellikleri bunun iyi bir örneğidir.

var cmd = new System.Data.SqlClient.SqlCommand() 
{ 
    Parameters = 
    { 
     new System.Data.SqlClient.SqlParameter() { ParameterName = "@p1", Value = "SomValue"} 
    }, 
    CommandText = "select 1 from Table1 where Value = @p1" 
}; 

Ayrıca, salt okunur özelliklerin değerlerini başlatmanıza izin verir.

bu makaleden hemen hemen kelimesi kelimesine Ödünç
//compiles and works 
var message = new MailMessage { To = { "[email protected]" } }; 

message = new MailMessage 
{ 
    // won't compile: To is read-only 
    To = new MailAddressCollection { "[email protected]" }, 
}; 

: http://www.codeducky.org/even-concise-c-object-initializers/

Yeni-az başlatıcı sözdizimi size kod biraz daha özlü yapmak ve salt okunur özelliklerini yapılandırmak için başlatma sözdizimini kullanmanıza olanak sağlar. Aslında, çoğu temel sınıf kitaplığı ve popüler .NET paketi sınıfları, toplama özellikleri için boş boş şablonunu izlediğinden, neredeyse her zaman onlar için yeni-olmayan sözdiziminden yararlanabilirsiniz. Son olarak, yeni olmayan başlatmayı kullanmak, aynı zamanda, bir nesnenin başlatıldığı varsayılan herhangi bir değerin yerinde bırakılmasını da sağlar.