1) Extension members — extension property, static extension va hatto operatorlar
Nima o‘zgardi: Endi extension'lar faqat metod emas; property va hatto static (turga tegishli) extension'larni ham e’lon qilish mumkin. Bundan tashqari, user-defined operatorlarni ham extension sifatida taqdim etish mumkin.
Nega foydali: Klaslarga yoki interface’larga tashqi paketlardan (utility) qulay "qo‘shimcha" funksionallik qo‘shish, original turlarni o‘zgartirmasdan kodni o‘qilishi yaxshilash mumkin.
Misol:
// extension block — instance receiver
extension<TSource>(IEnumerable<TSource> source)
{
// extension property (o'qish uchun)
public bool IsEmpty => !source.Any();
// extension method
public IEnumerable<TSource> WhereNot(Func<TSource, bool> predicate)
=> source.Where(x => !predicate(x));
}
// static extension members — turga tegishli
extension<TSource>(IEnumerable<TSource>)
{
public static IEnumerable<TSource> Identity => Enumerable.Empty<TSource>();
public static IEnumerable<TSource> operator +(IEnumerable<TSource> a, IEnumerable<TSource> b)
=> a.Concat(b);
}
Qo‘llanishi:
var arr = new List<int>();
bool empty = arr.IsEmpty; // instance extension property
var sum = IEnumerable<int>.Identity; // static extension property
(Manba: extension members).
2) fieldbacked properties (field kontekst kalit so‘zi)
Nima o‘zgardi: Endi property ichidagi field token yordamida explicit backing field yozmasdan get/set accessor'lariga body qo‘yish mumkin — kompilyator avtomatik backing field yaratadi.
Nega foydali: Kodni qisqartiradi va null tekshiruvchi logikani property ichida soddalashtirish imkonini beradi.
Misol — eski usul:
private string _msg;
public string Message
{
get { return _msg; }
set
{
if (value == null) throw new ArgumentNullException(nameof(value));
_msg = value;
}
}
C# 14 bilan (field backed):
public string Message
{
get;
set => field = value ?? throw new ArgumentNullException(nameof(value));
}
Eslatma: Agar sizning type’ingizda field nomli boshqa identifikator bo‘lsa, @field yoki this.field orqali chalkashlik oldini olish kerak.
3) Null-conditional assignment (?. assignment)
Nima o‘zgardi: ?. (null-conditional access) endi assignment va compound assignment (masalan +=) turgan joylarda ham ishlaydi — lekin ++/-- kabi increment/decrement ruxsat etilmaydi.
Nega foydali: Oldingi kabi if (obj != null) obj.Prop = ...; deb tekshirish shart emas — kod ixcham va xavfsizroq bo‘ladi.
Misol:
// oldingi usul
if (customer != null)
{
customer.Order = GetCurrentOrder();
}
// C# 14
customer?.Order = GetCurrentOrder();
Compound assignment:
user?.Score += points; // agar user null bo'lsa, o'ng taraf bahosi hisoblanmaydi
(Ammo user?.Count++ kabi incrementlar ruxsat etilmaydi).
4) nameof bilan ochilmagan (unbound) generic turlar
Nima o‘zgardi: nameof funksiyasiga endi unbound generic (masalan List<>) ham berish mumkin — natija tur nomi bo‘ladi ("List").
Misol:
Console.WriteLine(nameof(List<>)); // chiqaradi: List
Bu logging, exception yoki reflection yordamida nom olish operatsiyalarini soddalashtiradi.
5) First-class Span va ReadOnlySpan — qo‘shimcha implicit conversion'lar
Nima o‘zgardi: Span<T> va ReadOnlySpan<T> uchun til darajasida ko‘proq implicit conversion'lar qo‘shildi: ular T[] bilan ko‘proq holatlarda o‘zaro ishlashi mumkin, generik tip inferensiyasi soddalashadi, extension method receiver sifatida ishlatilishi yaxshilandi.
Nega foydali: Span yordamida "stack-based" yoki memory-safe high-performance kod yozish qulayroq; .NET’dagi string/byte[] manipulyatsiyalarida yangi konversiyalar kodni soddalashtiradi va ortiqcha kopi qilishni kamaytiradi.
Oddiy misol:
void ProcessSpan(Span<byte> span) { /* ... */ }
byte[] arr = new byte[100];
ProcessSpan(arr); // oldin explicit .AsSpan() kerak bo'lar edi; endi ko'proq holatda ishlashi mumkin
Tayyorlik: Span bilan ishlaganda e’tibor — ularni uzun muddatli saqlash (field) qilmaslik; ular stack yoki scope bilan bog‘liq bo‘lishi mumkin.
6) Lambda parametrlarida modifikatorlarni type yozmasdan ishlatish
Nima o‘zgardi: Endi lambda parametrlari uchun ref, in, out, scoped, ref readonly kabi modifikatorlarni tipni qaytarmasdan yozish mumkin.
Nega foydali: Lambda’larni qisqartiradi, ayniqsa ref yoki out bilan ishlaganda.
Misol:
delegate bool TryParse<T>(string text, out T result);
TryParse<int> parse = (string text, out int result) => int.TryParse(text, out result);
// C# 14: type yozmasdan modifier bilan
TryParse<int> parse2 = (text, out result) => int.TryParse(text, out result);
// yoki ref example
ActionRef(ref int x) => Console.WriteLine(x);
var a = (ref int value) => { value += 1; }; // misol uchun
(Params modifier hali ham tip talab qiladi).
7) Partial constructors va partial events
Nima o‘zgardi: Konstruktorlar va event’larni partial deb e’lon qilish mumkin — ya’ni bir deklaratsiya «defining» bo‘lib, ikkinchisi «implementing» bo‘ladi.
Nega foydali: Katta kodbazalarda generatorlar yoki source-generator lar bilan ishlaganda, bir qismi avtomatik yaratiladigan konstruktor/event implementatsiyalarini bo‘lish imkonini beradi.
Qoidalar:
- Har bir partial constructor/event uchun aniq bitta defining va bitta implementing deklaratsiya bo‘lishi kerak.
- Faol (implementing) konstruktor faqat
this()yokibase()initializer qo‘sha oladi. - Implementing event add/remove accessor’larini o‘z ichiga oladi; defining esa field-like event bo‘ladi.
8) User-defined compound assignment operators
Nima o‘zgardi: Endi siz +=, -=, *= kabi compound assignment operator’larini o‘zingiz aniqlay olasiz (til darajasida qo‘llab-quvvatlanadi).
Nega foydali: Turli matematik yoki domen-specific tiplarda to‘g‘ri semantic bilan compound operatorlarni qo‘llash mumkin.
Misol:
public struct MyVector
{
public int X, Y;
public MyVector(int x, int y) { X = x; Y = y; }
public static MyVector operator +(MyVector a, MyVector b) => new(a.X + b.X, a.Y + b.Y);
// compound assignment (foydalanuvchi aniqlovchi)
public static MyVector operator +=(MyVector a, MyVector b) => a + b;
}
Shunday qilib v1 += v2; ishlaganda aniq qanday bajarilishi belgilangan bo‘ladi.
Qanday holatlarda yangi feature’dan foydalanish tavsiya etiladi?
- Extension members: Agar siz utility kutubxonada ko‘p ishlatiladigan property yoki static yordamchi funksiyalarni joylashtirmoqchi bo‘lsangiz.
- Field-backed properties: Property ichida oddiy validatsiya yoki logging qo‘yish uchun — kodni ancha qisqartiradi.
- Null-conditional assignment: Nullable obyektlarga safe assignment yozishni ixchamlashtirish uchun.
- Span conversion: Performance-sensitive kodlarda (parsing, buffer manipulation) foydalaning.
- Lambda modifiers: Ref/in/out kerak bo‘lgan yuqori-performans kodlarda yoki existing delegate’lar bilan moslashish uchun.
- Partial constructors/events va user-defined compound assignment: Asosan kutubxona muhandislari, source-generatorlar yoki domen modeling holatlarida.
Xulosa
C# 14 — tilni yanada ixcham, o‘qilishi qulay, va performance-friendly qilishga qaratilgan o‘zgarishlarni olib keladi. Agar loyihangiz .NET 10’ga o‘tgan bo‘lsa, yangi imkoniyatlardan sekin-asta foydalanib, kodni soddalashtirish va xatoni kamaytirish mumkin. Batafsil rasmiy tavsif va feature specification uchun Microsoft sahifasiga murojaat qilishingiz mumkin.
Top comments (2)
Nice👌👌👌
brilliant