به صورت پیشفرض، رشتهها در زبان #C، از نوع UTF-16 تعریف شدهاند؛ درحالیکه اکثر رشتهها در دنیای اینترنت و پروتکلهای آن، از نوع UTF-8 هستند. برای کاهش سربار کارآیی این تبدیلها، اکنون در C# 11 میتوانید رشتهها را با پسوند u8 نیز معرفی کنید تا از ابتدای کار، به صورت UTF-8 پردازش شوند. یک مثال:
// C# 10
string utf16String = "Hello World";
byte[] array1 = Encoding.UTF8.GetBytes(utf16String);
// C# 11
ReadOnlySpan<byte> utf8String = "Hello World"u8;
byte[] array2 = utf8String.ToArray();
در اینجا نحوهی تعریف یک رشتهی UTF-8 را توسط پسوند u8 در مثال دوم مشاهده میکنید. این رشته با نوع
<ReadOnlySpan<byte معرفی میشود که به همراه عدم نیاز به استفاده از متد Encoding.UTF8.GetBytes قبلی و همچنین تخصیص حافظهی رشتهی UTF-16 آن در مثال اول است. اگر میخواهید معادل آرایهی تغییرپذیر آنرا (mutable array) داشته باشید، باید از متد ()ToArray بر روی آن استفاده کنید.
افزایش خوانایی رشتههای UTF-8 در C# 11
یکی دیگر از مزیتهای این روش تعریف، علاوه بر بالا رفتن کارآیی کار با رشتههای UTF-8، بالا بردن امکان خوانایی و درک آنها است. برای مثال AuthStringLiteral مثال زیر، همان معادل آرایهی AuthWithTrailingSpace است که خوانایی بیشتری دارد:
ReadOnlySpan<byte> AuthWithTrailingSpace = new byte[] { 0x41, 0x55, 0x54, 0x48, 0x20 };
ReadOnlySpan<byte> AuthStringLiteral = "AUTH "u8;
چند مثال دیگر:
var helloUtf8 = "hello"u8;// new byte[] { 0x68, 0x65, 0x6c, 0x6c, 0x6f }
var dogUtf8 = "dog"u8;// new byte[] { 0x64, 0x6f, 0x67 }
var catUtf8 = "cat"u8;// new byte[] { 0x63, 0x61, 0x74 }
محدودیتهای کار با رشتههای UTF-8 در C# 11
- UTF-8 string literals از نوع ثوابت زمان کامپایل نیستند و از نوع ثوابت زمان اجرا محسوب میشوند. به همین جهت برای مثال نمیتوان از آنها به عنوان مقادیر ثابت و پیشفرض پارامترهای متدها استفاده کرد.
- UTF-8 string literals را نمیتوان در عملیات
string interpolation مورد استفاده قرار داد. همچنین نمیتوان از $ و u8، بر روی یک رشتهی نهایی تولید شده، استفاده کرد.