Ряд мов використовує набори символів, які більше ніж набір значень типу char.
Японський і Китайський - можливо найбільш близькі приклади.
Бібліотека GNU C включає підтримку двох механізмів для роботи з розширеними наборами символів: багатобайтові символи і широкі символи. Ця глава описує, як використовувати ці механізми, і функції для перетворення між ними.
Якщо ваша система підтримує розширення символів, то вона підтримує їх, і як багатобайтові символи і як розширені символи. Бібліотека включає функції, які Ви можете використовувати, щоб перетворити між двома поданнями. Ці функції описані в цьому розділі.
Комп'ютерна система може підтримувати більше ніж один мультибайтних символьний код, і більше ніж один розширений символьний код. Користувач управляє вибором кодів через поточний стандарт для символьного класифікації (див. Главу 19 [Стандарти]). Кожен стандарт визначає специфічний мультибайтних символьний код і специфічний розширений символьний код. Вибір стандарту впливає на поведінку функцій перетворення в бібліотеці.
Деякі стандарти не підтримують ні розширені символи, ні нетривіальні багатобайтові символи. У цих стандартах, бібліотечні функції перетворення все ще працюють, навіть якщо, що вони в основному тривіальні.
Якщо Ви вибираєте ННовая стандарт для символьного класифікації, внутрішній параметр зсуву, підтримуваний цими функціями може стати спутаним, так що - не варто змінювати стандарт в той час як, Ви перебуваєте в середині обробки рядка.
У звичайному коді ASCII, послідовність символів послідовність байтів, і кожен символ - один байт. Це дуже просто, але враховує тільки 256 різних символів.
У мультибайтних символьному коді, послідовність символів послідовність байтів, але кожен символ може займати одні або більше послідовних байт послідовності.
Є багато різних способів проектування мультибайтних символьного коду; різні системи використовують різні коди. Специфічний спосіб кодування визначається позначенням базисних послідовностей байтів, які представляють одиночний символ і які символи вони заміняють. Код, який комп'ютер може фактично використовувати, повинен мати кінцеве число цих базисних послідовностей, і зазвичай жодна з них не довше ніж кілька символів.
Ці послідовності не мають однакову довжину. Фактично, багато з них - тільки один байт. Тому що базисні символи ASCII в проміжку від 0 до 0177 настільки важливі, що вони заміщають себе у всіх мультибайтних символьних кодах. Тобто байт, чиє значення від 0 до 0177 - завжди символ сам по собі. Символи, які більше ніж один байт, повинні завжди починатися з байта в проміжку від 0200 до 0377.
Значення 0 байта може використовуватися, щоб завершити рядок, точно як це часто використовується в рядку символів ASCII.
Визначення базисних послідовностей байтів, які представляють поодинокі символи автоматично дають значення більш довгим послідовностям байтів, більше ніж один символ. Наприклад, якщо послідовність два байта 0205 049 заміщає символ грецької альфи, то 0205 049 065 повинна замістити альфу, супроводжувану "" (код ASCII 065), а 0205 049 0205 049 повинна замістити дві альфи в рядку.
Якщо будь-яка послідовність байтів може мати більше ніж одне значення як послідовність символів, то мультибайтних код неоднозначний і небезпечний. Коди, які системи фактично використовують всі однозначні.
У більшості кодів, є деякі послідовності байтів, які не мають ніякого значення як символ або символи. Вони називаються неприпустимими.
Найпростіший можливий мультибайтних код - тривіальний:
Базисні послідовності складаються з одиночних байтів.
Даний специфічний код не використовує багатобайтові символи взагалі. Він не має ніяких неприпустимих послідовностей. Але він може обробляти тільки 256 різних символів.
Ось інший можливий код, який може обробляти 9376 різних символів:
Базисні послідовності складаються з- одиночних байтів зі значеннями в проміжку від 0 до 0237.
- двох-байтових послідовностей, в яких обидва байта мають значення в проміжку від 0240 до 0377.
Цей код або подібний використовується на деяких системах, щоб представити Японські символи. Неприпустимі послідовності - ті, які складаються з непарного числа послідовних байтів в проміжку від 0240 до 0377.
Ось інший мультибайтних код, який може обробляти більше різних розширених символів, фактично, майже тридцять мільйонів:
Базисні послідовності складаються з- одиночних байтів зі значеннями в проміжку 0 до 0177.
- послідовностей до чотирьох байтів, в яких перший байт знаходиться в проміжку від 0200 до 0237, а решту байти знаходяться в проміжку від 0240 до 0377.
Ось інший варіант, який має перевагу: при видаленні останнього байта або байтів допустимого символу, ніколи не може з'явитися інший допустимий символ.
Базисні послідовності складаються з- одиночних байтів зі значеннями в проміжку від 0 до 0177.
- двох-байтових послідовностей, в яких перший байт знаходиться в проміжку від 0200 до 0207, а другий байт знаходяться в проміжку від 0240 до 0377.
- трьох-байтових послідовностей, в яких перший байт знаходиться в проміжку від 0210 до 0217, а інші байти знаходяться в проміжку від 0240 до 0377.
- чотирьох-байтових послідовностей, в яких перший байт знаходиться в проміжку від 0220 до 0227, а інші Байтала знаходяться в проміжку від 0240 до 0377.
Число можливих мультибайтних кодів дуже велике. Але дана комп'ютерна система буде підтримувати не більш декількох різних кодів. (Один з цих кодів може враховувати тисячі різних символів.) Інша комп'ютерна система може підтримувати повністю відмінний код. Бібліотечні засоби, описані в цьому розділі корисні, тому що вони описують подробиці мультибайтних коду специфічної комп'ютерної системи, хоча ваші програми не повинні знати.
Ви можете використовувати спеціальні стандартні макроси, щоб з'ясувати максимальне можливе число байтів символу в поточному мультибайтних коді іпользуются MB_CUR_MAX, а максимум для будь-якого мультибайтних коду, що забезпечується на вашому комп'ютері міститься в MB_LEN_MAX. Це - максимальна довжина мультибайтних символу для будь-якого забезпечується стандарту. Вона визначена в "limits.h". Ця макрокоманда відображає (можливо не-константу) позитивне целочисленное вираз, яке є максимальним числом байтів в мультибайтних символі в поточному стандарті. Значення ніколи не більше ніж MB_LEN_MAX.
MB_CUR_MAX визначено в "stdlib.h".
Що трапляється, якщо Ви пробуєте передавати рядок, що містить багатобайтові символи функції, яка не знає про них? Зазвичай, така функція обробляє рядок як послідовність байтів, і інтерпретує деякі значення особливо; всі інші значення байтів "звичайні". Якщо мультибайтних символ не містить спеціальне значення байта, функція повинна обробити його, як ніби це були окремі звичайні символи.
Розширені символи набагато простіше ніж багатобайтові символи. Вони - просто символи з більше, ніж вісьмома бітами, так, щоб вони мали місце для більше, ніж 256 різних кодів. Розширений символьний тип даних wchar_t, має досить великий діапазон, щоб включати розширених символьні коди також як традиційні коди ASCII.
Якщо ваша система підтримує розширені символи то кожен розширений символ має і розширений символьний код і відповідну багатобайтове базисну послідовність.
В цьому розділі, термін код використовується, щоб звернутися до одиночного розширеному символьному об'єкту, щоб підкреслити відмінність від типу даних char.
Функція mbstowcs перетворює рядок мультибайтних символів в масив розширених символів. Функція wcstombs робить зворотний процес. Ці функції оголошені в заголовному файлі "stdlib.h".
У більшості програм, ці функції - єдина Ваша потреба в перетворенні між розширеними рядками і мультибайтних символьними рядками. Але вони мають обмеження. Якщо ваші дані не з нульовим символом в кінці або - в повному обсязі в ядрі відразу, Ви можливо повинні використовувати функції перетворення низького рівня, щоб перетворити один символ за раз. Див. Розділ 18.7 [Перетворення Одного Символу]. mbstowcs ( "мультибайтних рядок в рядок розширених символів") функція перетворює рядок з нульовим символом в кінці мультибайтних символів в масив розширених символів, зберігаючи але лише size розширених символів в масиві, що починається в wstring. Порожній символ завершення розраховується в size, так що, якщо розмір менше, ніж фактичне число розширених символів, що прямують з рядка, ніякої порожньої символ завершення НЕ буде збережений.
Перетворення символів з рядка починається з початковим параметром регістра.
Якщо неприпустима мультибайтних символьна послідовність знайдена, функція повертає значення -1. Інакше, вона повертає число розширених символів, збережених в масиві wstring. Це число не включає порожній символ завершення, який присутній, якщо число менше, ніж size.
Ось приклад, який показує, як перетворювати рядок мультибайтних символів, резервуючи достатній простір для результату. wcstombs перетворює масив розширених символів з нульовим символом в кінці в рядок, що містить багатобайтові символи, зберігаючи але лише size байт, починаючи з string.
Якщо знайдений код, який не відповідає допустимому мультибайтних символу, то ця функція повертає значення -1. Інакше, повертається значення - число байтів, збережених в масиві. Це число не включає порожній символ завершення, який присутній, якщо число - менше ніж size.
Значення, що повертається mblen відрізняє три можливості: перші size байт рядка починаються з допустимого мультибайтних символу, вони починаються з неприпустимою послідовності байтів або включають тільки частину символу, або string вказує на порожній рядок (порожній символ).
Для допустимого мультибайтних символу, mblen повертає число байтів в цьому символі (завжди по крайней мере 1, і ніколи не більше ніж size). Для неприпустимою послідовності байтів, mblen повертає -1. Для порожнього рядка, вона повертає 0.
Якщо мультибайтних символьний код використовує символи зміни регістру, то mblen, підтримує і модифікує параметр регістра. Якщо Ви викликаєте mblen з порожнім покажчиком для рядка, вона инициализирует параметр регістра до стандартного початкового значення. Див. Розділ 18.9 [Параметра Регістру].
Функція mblen оголошена в "stdlib.h".
Ви можете перетворювати багатобайтові символи в розширені символи по одному mbtowc функцією. Wctomb функція робить протилежне. Ці функції оголошені в "stdlib.h". Mbtowc перетворює перший мультибайтних символ в string в відповідний розширений символьний код. Вона зберігає результат в * result. Mbtowc ніколи не досліджує більше ніж size байт. (Ідея полягає в тому, щоб забезпечити для size число байтів даних, яке Ви маєте.) Mbtowc з непорожній рядком Значення, що повертається mblen відрізняє три можливості: перші size байт рядка починаються з допустимого мультибайтних символу, вони починаються з неприпустимою послідовності байтів або включають тільки частину символу, або string вказує на порожній рядок (порожній символ).
Для допустимого мультибайтних символу, mbtowc перетворює його в розширений символ, зберігає його в * result, і повертає число байтів в тому символі (завжди по крайней мере 1, і ніколи не болольше ніж size).
Для неприпустимою послідовності байтів, mbtowc повертає 1. Для порожнього рядка, вона повертає 0, також зберігаючи 0 в * result. Функція wctomb перетворює розширений символьний код wchar в відповідну багатобайтове символьну послідовність, і зберігає результат в байтах, починаючи з string. Wctomb з непорожній рядком відрізняє три можливості для wchar: допустимий розширений символьний код (той, який може транслюватися в мультибайтних символ), неприпустимий код, і 0.
Якщо wchar - неприпустимий розширений символьний код, wctomb повертає -1. Якщо wchar - 0, вона повертає 0, також зберігаючи 0 в * string.
Виклик цієї функції з нульовим wchar аргументом, коли рядок - не порожній символ, має побічний ефект переініціалізація збереженого параметру регістра також як збереження мультибайтних символу 0 і повернення 0.
Ось приклад, який читає многобайтовоий-символьний текст з дескриптора input і записує відповідні розширені символи в описувач output. Ми повинні перетворити символи один за іншим в цьому прикладі, тому що mbstowcs нездатна продовжитися після порожнього символу, і не може справлятися з очевидно неприпустимим частковим символом, читаючи велику кількість введення.
У деяких мультибайтних символьних кодах, значення будь-специфічної послідовності байтів не фіксоване; воно залежить від інших послідовностей розглянутих раніше в тій же самій рядку. Зазвичай є тільки кілька послідовностей, які можуть змінювати значення інших послідовностей; ці деякі називаються послідовностями регістрів, і ми говоримо, що вони встановлюють параметр регістра для інших послідовностей, які підуть.
Щоб проілюструвати стан регістра і послідовності регістрів, припустімо, що ми встановлюємо, що послідовність 0200 (тільки один байт) вводить Японський режим, в якому пари байтів в проміжку від 0240 до 0377 є поодинокими символами, в той час як 0201 вводить Латинський-1 режим , в якому поодинокі байти в проміжку від 0240 до 0377 є символами, і інтерпретуються згідно набору символів Latin-1 Міжнародної організації зі стандартизації. Це - мультибайтних код, який має два альтернативних стану регістра ( "Японський режим" і "Латинський-1 режим"), і дві послідовності регістрів, які визначають специфічні стани регістра.
Ось приклад використання mblen з дотриманням цих правил: Функції mblen, mbtowc і wctomb не використовуються при використанні мультибайтних коду, який використовує стан регістра. Однак, ніякі інші бібліотечні функції не викликають ці функції, так що Ви не повинні хвилюватися щодо цього.