Not
Bu sayfaya erişim yetkilendirme gerektiriyor. Oturum açmayı veya dizinleri değiştirmeyi deneyebilirsiniz.
Bu sayfaya erişim yetkilendirme gerektiriyor. Dizinleri değiştirmeyi deneyebilirsiniz.
11.1 Genel
Desen, işleç (is§12.14.12), bir switch_statement (§13.8.3) ve switch_expression (§12.11) ile gelen verilerin karşılaştırılacağı veri şeklini ifade etmek için kullanılabilen söz dizimsel bir formdur. Desenler özyinelemeli olabilir, böylece verilerin bölümleri alt desenlerle eşleştirilebilir.
Desen, çeşitli bağlamlardaki bir değere göre test edilir:
- Switch deyiminde, bir servis talebi etiketinin deseni switch deyiminin ifadesinde test edilir.
- bir is-pattern işlecinde, sağ taraftaki desen soldaki ifadeye göre test edilir.
- Switch ifadesinde, switch_expression_armdeseni switch-expression'ın sol tarafındaki ifadeye göre test edilir.
- İç içe bağlamlarda alt desen, desen formuna bağlı olarak özelliklerden, alanlardan alınan veya diğer giriş değerlerinden dizine alınan değerlerle test edilir.
Bir desenin sınandığı değer, desen giriş değeri olarak adlandırılır.
11.2 Desen formları
11.2.1 Genel
Bir desen aşağıdaki formlardan birine sahip olabilir:
pattern
: declaration_pattern
| constant_pattern
| var_pattern
| positional_pattern
| property_pattern
| discard_pattern
;
Bazı desenleryerel bir değişkenin bildirimiyle sonuçlanabilir.
Her desen formu, desenin uygulanabileceği giriş değerleri için tür kümesini tanımlar. Desen, değerleri P eşleşebilecek türler arasındaysa, T bir tür için geçerlidirT Için geçerli değilse P , bir programda desen giriş değeriyle (§11.1) T eşleşecek şekilde görüntüleniyorsa P derleme zamanı hatasıdır T.
Örnek: Aşağıdaki örnek, derleme zamanı türü
volduğundanTextReaderderleme zamanı hatası oluşturur. TüründekiTextReaderbir değişkenin hiçbir zaman ilestringbaşvuru uyumlu bir değeri olamaz:TextReader v = Console.In; // compile-time type of 'v' is 'TextReader' if (v is string) // compile-time error { // code assuming v is a string }Ancak, derleme zamanı türü
volduğundanobjectaşağıdakiler derleme zamanı hatası oluşturmaz. Türündeobjectbir değişken, ilestringbaşvuru uyumlu bir değere sahip olabilir:object v = Console.In; if (v is string s) { // code assuming v is a string }son örnek
Her desen formu, desenin çalışma zamanındaki değerle eşleşdiği değer kümesini tanımlar.
Desen eşleştirme sırasında işlemlerin ve yan etkilerin değerlendirilmesi sırası ( Deconstructiçindeki yöntemlerin System.ITupleçağrıları, özellik erişimleri ve çağrıları) belirtilmez.
11.2.2 Bildirim düzeni
declaration_pattern, bir değerin belirli bir türe sahip olup olmadığını test etmek ve test başarılı olursa isteğe bağlı olarak bu türdeki bir değişkende değer sağlamak için kullanılır.
declaration_pattern
: type simple_designation
;
simple_designation
: discard_designation
| single_variable_designation
;
discard_designation
: '_'
;
single_variable_designation
: identifier
;
Belirteci _ olan bir simple_designation, single_variable_designation yerine discard_designation olarak kabul edilir.
Değerin çalışma zamanı türü, is-type işlecinde (§12.14.12.1) belirtilen kurallar kullanılarak desendeki türe göre test edilir. Test başarılı olursa, desen bu değerle eşleşir .
Tür null atanabilir bir değer türü (§8.3.12) veya null atanabilir başvuru türü (§8.9.3) ise derleme zamanı hatasıdır. Bu desen formu hiçbir zaman bir değerle null eşleşmez.
Not: is-type ifadesi
e is Tve bildirim desenie is T _null atanabilir bir tür olmadığında eşdeğerdirT. son not
Bir desen giriş değeri (§11.1) e verildiğinde, simple_designationdiscard_designation ise atma (§9.2.9.2) değerini belirtir ve e değeri hiçbir şeye bağlı değildir. (Bu noktada adıyla _ bildirilen bir değişken kapsam içinde olsa da, bu adlandırılmış değişken bu bağlamda görülmez.) Aksi takdirde , simple_designationsingle_variable_designation, verilen tanımlayıcı tarafından adlandırılan belirtilen türde bir yerel değişken (§9.2.9) kullanıma sunulur. Bu yerel değişkene, desen değerle eşleştiğinde desen giriş değerinin değeri atanır.
Desen giriş değerinin statik türünün ve verilen türün belirli birleşimleri uyumsuz olarak kabul edilir ve derleme zamanı hatasına neden olur. Statik türdeki E bir değerin, bir kimlik dönüştürmesi, örtük veya açık başvuru dönüştürmesi, bir kutulama dönüştürmesi veya 'den gelen kutulama açma dönüştürmesi varsa ya da açık bir türse TE (T) türüyle E uyumlu desenle uyumluT Bir türü T adlandıran bildirim deseni, geçerlidir.
Not: Açık türler için destek en çok yapı veya sınıf türleri olabilecek türleri denetlerken yararlı olabilir ve kutulamadan kaçınılmalıdır. son not
Örnek: Bildirim deseni, başvuru türlerinin çalışma zamanı türü testlerini gerçekleştirmek için kullanışlıdır ve deyiminin yerini alır
var v = expr as Type; if (v != null) { /* code using v */ }biraz daha kısa
if (expr is Type v) { /* code using v */ }son örnek
Örnek: Bildirim deseni, null atanabilir türlerin değerlerini test etmek için kullanılabilir: değer null olmayan ve
Nullable<T>Tise tür deseniT2 id(veya kutuluT2) bir tür deseniTile eşleşir ya da bazı temel türü veya arabirimi.TÖrneğin, kod parçasındaint? x = 3; if (x is int v) { /* code using v */ }deyiminin
ifkoşulu çalışma zamanındadırtrueve değişkenv, bloğun içindeki türün3değeriniinttutar. Blok sonrasında değişkenvkapsam içindedir, ancak kesinlikle atanmamış olur. son örnek
11.2.3 Sabit deseni
Bir desen giriş değerinin (§11.1) değerini verilen sabit değerle test etmek için bir constant_pattern kullanılır.
constant_pattern
: constant_expression
;
sabit ifadesinden türüne PT geçerlidir.P
Sabit bir desen içinP, dönüştürülen değeri
- Desen giriş değerinin türü bir tamsayı türü veya bir numaralandırma türüyse, desenin sabit değeri bu türe dönüştürülür; yoksa
- Desen giriş değerinin türü bir tamsayı türünün veya bir sabit sabit türünün null atanabilir sürümüyse, desenin sabit değeri temel alınan türüne dönüştürülür; yoksa
- desenin sabit değerinin değeri.
Esahip sabit bir desen P verildiğinde,
- e tamsayı türüne veya sabit listesi türüne veya bunlardan birinin null atanabilir bir biçimine ve v tamsayı türüne sahipse, ifadenin
Psonucu ise desen ; aksi takdirde - deseni
P.
Örnek:
switchAşağıdaki yöntemdeki deyimi, büyük/küçük harf etiketlerinde beş sabit desen kullanır.static decimal GetGroupTicketPrice(int visitorCount) { switch (visitorCount) { case 1: return 12.0m; case 2: return 20.0m; case 3: return 27.0m; case 4: return 32.0m; case 0: return 0.0m; default: throw new ArgumentException(...); } }son örnek
11.2.4 Var deseni
var_pattern her değerle eşleşir. Başka bir ifadeyle, var_pattern ile desen eşleştirme işlemi her zaman başarılı olur.
var_pattern her tür için geçerlidir.
var_pattern
: 'var' designation
;
designation
: simple_designation
| tuple_designation
;
tuple_designation
: '(' designations? ')'
;
designations
: designation (',' designation)*
;
Bir desen giriş değeri (§11.1) e verildiğinde, atamadiscard_designation ise atılan değeri (§9.2.9.2) belirtir ve e değeri hiçbir şeye bağlı değildir. (Bu ada sahip bildirilen bir değişken bu noktada kapsam içinde olsa da, bu adlandırılmış değişken bu bağlamda görülmez.) Aksi takdirde, atamasingle_variable_designation ise çalışma zamanında e değeri, türü statik e türü olan ve desen giriş değeri bu yerel değişkene atanmış olan bu adın yeni tanıtılan yerel değişkenine (§9.2.9) bağlıdır.
Advar, bir var_pattern kullanıldığı bir türe bağlanacaksa bu bir hatadır.
Atama bir tuple_designation ise, desen form (vargösterimininpositional_pattern (§11.2.5) eşdeğerdir, ...
)burada, tuple_designation içinde bulunanlar olarak ifadeedilir. Örneğin, desen var (x, (y, z)) ile (var x, (var y, var z))eşdeğerdir.
11.2.5 Konumsal desen
positional_pattern giriş değerinin olmadığını nulldenetler, uygun Deconstruct bir yöntem (§12.7) çağırır ve sonuçta elde edilen değerlerde daha fazla desen eşleştirmesi gerçekleştirir. Ayrıca, giriş değerinin türü öğesini içeren Deconstructtürle aynı olduğunda veya giriş değerinin türü bir tanımlama grubu türündeyse veya giriş object değerinin türü veya System.ITuple ise ve ifadenin çalışma zamanı türü uygulandığında System.ITupletanımlama grubu benzeri bir desen söz dizimini (sağlanan tür olmadan) destekler.
positional_pattern
: type? '(' subpatterns? ')' property_subpattern? simple_designation?
;
subpatterns
: subpattern (',' subpattern)*
;
subpattern
: pattern
| identifier ':' pattern
;
Bir giriş değerinin desen türü(alt desenleriyle) eşleşmesi göz önüne alındığında, türü içinde erişilebilir bildirimleri Deconstructaranarak ve bunlar arasında, yapısızlaştırma bildirimiyle aynı kurallar kullanılarak bir yöntem seçilir.
Bir positional_pattern türü atlarsa, tanımlayıcısı olmayan tek bir alt sayfaya sahipse, property_subpattern yoksa ve simple_designation yoksa hatadır. Bu, parantez içindeki bir constant_pattern ile positional_pattern arasında ayrımlar.
Listedeki desenlerle eşleşecek değerleri ayıklamak için,
- Tür atlanırsa ve giriş ifadesinin türü bir tanımlama grubu türüyse, alt ekran sayısı tanımlama grubunun kardinalitesi ile aynı olmalıdır. Her tanımlama grubu öğesi karşılık gelen alt çizgiyle eşleştirilir ve bunların tümü başarılı olursa eşleşme başarılı olur. Herhangi bir alt çizginintanımlayıcısı varsa, bu, tanımlama grubu türündeki karşılık gelen konumda bir tanımlama grubu öğesini adlandıracaktır.
- Aksi takdirde, uygun
Deconstructbir türün üyesi olarak varsa, giriş değerinin türü türle desen uyumlu değilse derleme zamanı hatasıdır. Çalışma zamanında giriş değeri türe göre test edilir. Bu başarısız olursa, konumsal desen eşleşmesi başarısız olur. Başarılı olursa, giriş değeri bu türe dönüştürülür veDeconstructçıkış parametrelerini almak için derleyici tarafından oluşturulan yeni değişkenlerle çağrılır. Alınan her değer ilgili alt çizgiyle eşleştirilir ve bunların tümü başarılı olursa eşleşme başarılı olur. Herhangi bir alt belgenintanımlayıcısı varsa, bu, ilgili konumundaki bir parametreyiDeconstructadlandıracaktır. - Aksi takdirde, tür atlanırsa ve giriş değeri
objecttürü veya örtük başvuru dönüştürmesi tarafından dönüştürülebilecekSystem.ITuplebir tür ise ve alt grafikler arasında hiçbir tanımlayıcı görünmezse, eşleşme kullanırSystem.ITuple. - Aksi takdirde, desen bir derleme zamanı hatasıdır.
Çalışma zamanında alt grafiklerin eşleşme sırası belirtilmemiştir ve başarısız bir eşleşme tüm alt grafiklerle eşleşmeye çalışmayabilir.
Örnek: Burada, bir ifade sonucunun yapısını kaldıracak ve sonuçta elde edilen değerleri ilgili iç içe yerleştirilmiş desenlerle eşleştireceğiz:
static string Classify(Point point) => point switch { (0, 0) => "Origin", (1, 0) => "positive X basis end", (0, 1) => "positive Y basis end", _ => "Just a point", }; public readonly struct Point { public int X { get; } public int Y { get; } public Point(int x, int y) => (X, Y) = (x, y); public void Deconstruct(out int x, out int y) => (x, y) = (X, Y); }son örnek
Örnek: Tanımlama grubu öğelerinin ve Deconstruct parametrelerinin adları aşağıdaki gibi konumsal bir düzende kullanılabilir:
var numbers = new List<int> { 10, 20, 30 }; if (SumAndCount(numbers) is (Sum: var sum, Count: var count)) { Console.WriteLine($"Sum of [{string.Join(" ", numbers)}] is {sum}"); } static (double Sum, int Count) SumAndCount(IEnumerable<int> numbers) { int sum = 0; int count = 0; foreach (int number in numbers) { sum += number; count++; } return (sum, count); }Üretilen çıkış şu şekildedir:
Sum of [10 20 30] is 60son örnek
11.2.6 Özellik düzeni
property_pattern, giriş değerinin olup olmadığını nulldenetler ve erişilebilir özelliklerin veya alanların kullanımıyla ayıklanan değerlerle özyinelemeli olarak eşleşir.
property_pattern
: type? property_subpattern simple_designation?
;
property_subpattern
: '{' '}'
| '{' subpatterns ','? '}'
;
bir property_patternalt boyasıtanımlayıcı içermiyorsa bu bir hatadır.
Tür null atanabilir bir değer türü (§8.3.12) veya null atanabilir başvuru türü (§8.9.3) ise derleme zamanı hatasıdır.
Not: Null denetim deseni önemsiz bir özellik deseninin dışında kalır. Dizenin
snull olmadığını denetlemek için aşağıdaki formlardan herhangi birini yazabilirsiniz:#nullable enable string s = "abc"; if (s is object o) ... // o is of type object if (s is string x1) ... // x1 is of type string if (s is {} x2) ... // x2 is of type string if (s is {}) ...son note ifadesininproperty_pattern_list
}desen türüyle{eşleşmesi göz önüne alındığında, e ifadesi türe göre belirlenen T türüyle desen uyumlu değilse derleme zamanı hatasıdır. Tür yoksa, türün statik e türü olduğu varsayılır. property_pattern_list sol tarafında görünen tanımlayıcıların her biri erişilebilir bir okunabilir özellik veya T alanı belirlemeli. property_pattern simple_designation varsa, T türünde bir desen değişkeni bildirir.
Çalışma zamanında ifade T'ye karşı test edilir. Bu başarısız olursa özellik deseni eşleşmesi başarısız olur ve sonuç olur false. Başarılı olursa, her property_subpattern alanı veya özelliği okunur ve değeri ilgili desenle eşleştirilir. Tüm eşleşmenin false sonucu yalnızca bunlardan herhangi birinin sonucu ise olur false. Alt yordamların eşleştirilme sırası belirtilmez ve başarısız bir eşleşme çalışma zamanında tüm alt yordamları test etmeyebilir. Eşleşme başarılı olursa ve property_pattern simple_designation bir single_variable_designation ise, bildirilen değişkene eşleşen değer atanır.
property_pattern, anonim türlerle desen eşleştirmek için kullanılabilir.
Örnek:
var o = ...; if (o is string { Length: 5 } s) ...son örnek
Örnek: Aşağıdaki gibi, bir çalışma zamanı türü denetimi ve bir değişken bildirimi bir özellik desenine eklenebilir:
Console.WriteLine(TakeFive("Hello, world!")); // output: Hello Console.WriteLine(TakeFive("Hi!")); // output: Hi! Console.WriteLine(TakeFive(new[] { '1', '2', '3', '4', '5', '6', '7' })); // output: 12345 Console.WriteLine(TakeFive(new[] { 'a', 'b', 'c' })); // output: abc static string TakeFive(object input) => input switch { string { Length: >= 5 } s => s.Substring(0, 5), string s => s, ICollection<char> { Count: >= 5 } symbols => new string(symbols.Take(5).ToArray()), ICollection<char> symbols => new string(symbols.ToArray()), null => throw new ArgumentNullException(nameof(input)), _ => throw new ArgumentException("Not supported input type."), };Üretilen çıkış şu şekildedir:
Hello Hi! 12345 abcson örnek
11.2.7 Atma düzeni
Her ifade atma deseni ile eşleşir ve bu da ifadenin değerinin atılmasıyla sonuçlanır.
discard_pattern
: '_'
;
Form relational_expression deseninin relational_expression atma deseninin kullanılması veya switch_labelisdeseni olarak kullanılması derleme zamanı hatasıdır.
Not: Bu gibi durumlarda, herhangi bir ifadeyi eşleştirmek için at
var _ile bir var_pattern kullanın. son not
Örnek:
Console.WriteLine(GetDiscountInPercent(DayOfWeek.Friday)); Console.WriteLine(GetDiscountInPercent(null)); Console.WriteLine(GetDiscountInPercent((DayOfWeek)10)); static decimal GetDiscountInPercent(DayOfWeek? dayOfWeek) => dayOfWeek switch { DayOfWeek.Monday => 0.5m, DayOfWeek.Tuesday => 12.5m, DayOfWeek.Wednesday => 7.5m, DayOfWeek.Thursday => 12.5m, DayOfWeek.Friday => 5.0m, DayOfWeek.Saturday => 2.5m, DayOfWeek.Sunday => 2.0m, _ => 0.0m, };Üretilen çıkış şu şekildedir:
5.0 0.0 0.0Burada, numaralandırmanın karşılık gelen üyesi olmayan tüm tamsayı değerlerini işlemek
nulliçin atma deseniDayOfWeekkullanılır. Bu, ifadenin tüm olası giriş değerlerini işlemesiniswitchgaranti eder. son örnek
11.3 Desen alt devamı
Switch deyiminde, bir servis talebinin deseninin önceki korumasız vaka kümesi (§13.8.3) tarafından çıkarılması hatadır. Bu, herhangi bir giriş değerinin önceki durumlardan biriyle eşleştirildiği anlamına gelir. Aşağıdaki kurallar, bir desen kümesinin belirli bir desenin ne zaman alt toplamını verdiğini tanımlar:
Bu desenin P bir desen sabitle K eşleşirP.
Bir dizi desen Q dizinini oluşturur:
-
Psabit bir desendir ve kümedekiQdesenlerden herhangi biri 'nin dönüştürülmüş değeriyle eşleşirP -
Pbir var desenidir ve desenQkümesi desen giriş değerinin türü (§11.1) için kapsamlıdır -
PtürüneTsahip bir bildirim desenidir ve desenQkümesi tür için kapsamlıdırT(§11.4).
11.4 Desen tükenmişliği
Boş değer dışındaki her olası değer için kümedeki bir desen geçerliyse, kayıt dışı olarak bir tür için desen kümesi çok kapsamlıdır. Aşağıdaki kurallar, bir tür için bir dizi desenin ne zaman kapsamlı olduğunu tanımlar:
Aşağıdaki koşullardan herhangi biri geçerliyse, bir tür için bir dizi desen Q kapsamlıdır:T
-
Ttamsayı veya sabit listesi türü ya da bunlardan birinin null atanabilir bir sürümüdür ve 'nin null atanamaz temel türündekiTher olası değer için içindeki bazı desenlerQbu değerle eşleşir; veya - içindeki
Qbazı desenler var desenidir; veya - içindeki
Qbazı desenler türü için birDve bir kimlik dönüştürmesi, örtük başvuru dönüştürmesi veya ile arasında bir kutulama dönüştürmesiTDvardır.
Örnek:
static void M(byte b) { switch (b) { case 0: case 1: case 2: ... // handle every specific value of byte break; // error: the pattern 'byte other' is subsumed by the (exhaustive) // previous cases case byte other: break; } }son örnek
ECMA C# draft specification