Tester64 420 / 357 / 47 Регистрация: 22.05.2013 Сообщений: 2,518 |
||||||||
31.08.2014, 19:10. Показов 21955. Ответов 22 Метки нет (Все метки) Нашел пример:
Шикарно работает в консоли, но ОЧЕНЬ надо пределать его в функции со String
Но знаний по преобразованию строк в char и назад не хватает! Только начал вычитывать, а функция нужна срочно!
0 |
Ryzhikov_A 6 / 6 / 0 Регистрация: 14.10.2012 Сообщений: 36 |
||||||||
31.08.2014, 20:09 |
||||||||
Для перехода от string к const char* (неизменяемому массиву символов в куче) используйте метод c_str():
Для создания строки типа string из массива символов просто вызовите конструктор.
Добавлено через 6 минут
1 |
420 / 357 / 47 Регистрация: 22.05.2013 Сообщений: 2,518 |
|
31.08.2014, 21:04 [ТС] |
|
Вторая часть кода подошла, но не первая. Она работает, но мне нужно другое:
0 |
Ryzhikov_A 6 / 6 / 0 Регистрация: 14.10.2012 Сообщений: 36 |
||||
31.08.2014, 21:22 |
||||
Аналогично
1 |
DrOffset 19456 / 10069 / 2451 Регистрация: 30.01.2014 Сообщений: 17,749 |
||||
31.08.2014, 21:49 |
||||
Сообщение было отмечено Tester64 как решение РешениеTester64, тут еще ведь нужно понимать, что L»строка» — это не UTF8. Это скорее UTF16 или USC2, если рассматривать windows.
1 |
Tester64 420 / 357 / 47 Регистрация: 22.05.2013 Сообщений: 2,518 |
||||
31.08.2014, 22:25 [ТС] |
||||
ИДЕАЛЬНО!
(я как новичок этого не знал)
0 |
383 / 281 / 31 Регистрация: 04.09.2009 Сообщений: 1,225 |
|
01.09.2014, 01:47 |
|
Хм, все бегут без оглядки от CP1251 и от всяких понаехавших «кодовых страниц», а тут наоборот, UTF-8 не нравится
0 |
19456 / 10069 / 2451 Регистрация: 30.01.2014 Сообщений: 17,749 |
|
01.09.2014, 01:50 |
|
Сообщение от gromo Хм, все бегут без оглядки от CP1251, а тут наоборот, UTF-8 не нравится Пусть сам налетает на все грабли
0 |
420 / 357 / 47 Регистрация: 22.05.2013 Сообщений: 2,518 |
|
01.09.2014, 03:48 [ТС] |
|
Сообщение от gromo Хм, все бегут без оглядки от CP1251 и от всяких понаехавших «кодовых страниц», а тут наоборот, UTF-8 не нравится Сообщение от DrOffset про пользу юникода и почему подстраиваться под устаревшую вин консоль (с дос кодировкой по умолчанию) не обязательно Считайте капризом! Работаю под виндой. Пишу в блокноте (notepad++) без IDE. Компилирую батником. Код не большой. Самое главное — скорость сборки. А не удобство редактора и выпадающие подсказки. Результат вывожу в универсальную виндовую консоль. Как перепрошить всю винду с анси на юникод не знаю, да и не хочу — другие программы «крокозябры» писать будут (включая RAR и 7ZIP). Написал функцию — Rep(«привет мир») — выводящую строку с результатом в консоль. В нее-же зашил анси. Все исходники (текстовики СРР и Н) храню в юникоде (где-то вычитал что это любимая кодировка g++ и NDK). Rep вызываю редко, но не хочу заморачиваться с перекодированием системной консоли на чужих машинах (или писать транслитом или вспоминать как это зовется на английском). Под линукс (если перейду) сделаю другой Rep. Под андроид третий (уже сделал). Команда одна, но сама решает что и как выводить. И главное без заморочек с кодировкой на входе. Смогу одной константой отключить перекодирование, но пока… Так удобнее! Да и учусь я пока. Простые утилитки пишу, базовые конструкции тестирую… Пока-что перевод нужен был ТОЛЬКО для отладочных сообщений в консоль, хотя бывает необходимость и при работе с файлами кодировку заменить и со старым сервером через сеть пообщаться… Пусть себе лежит в коллекции. Заодно понял как строки конвертировать между разными типами (char-wchar-string), а это похоже крайне необохдимые знания в с++ p.s. Для ускорения вызова батников даже утилиту на делфи написал для вызова батников по горячим клавишам. И их принудильного перезапуска (перекомпиляция). ИМХО самое быстрое изученение… IDE много перепробовал — все тормозят сильно. Сборка пустышки под VC++ занимала минимум 20-30 секунд. Как и под DevCPP. Консоль (когда тормозит) за 7-8 секунд собирает, а если ускоряется около 3х секунд (почти догнал паскаль)…
0 |
Ушел с форума 16478 / 7441 / 1187 Регистрация: 02.05.2013 Сообщений: 11,617 Записей в блоге: 1 |
|
01.09.2014, 09:43 |
|
Сообщение от Tester64 Как перепрошить всю винду с анси на юникод не знаю, да и не хочу — другие программы «крокозябры» писать будут (включая RAR и 7ZIP). Не нужно ничего «перепрошивать», Windows уже лет 15 юникодная изнутри.
0 |
Модератор 5287 / 2375 / 342 Регистрация: 20.02.2013 Сообщений: 5,773 Записей в блоге: 20 |
|
01.09.2014, 09:54 |
|
Сообщение от DrOffset Я тут сперва написал большой пост про пользу юникода и почему подстраиваться под устаревшую вин консоль (с дос кодировкой по умолчанию) не обязательно, но потом стер. Ну и зачем стёр? Многим наверное было бы и полезно и интересно. Мне вот, например, интересно.
0 |
2687 / 2259 / 244 Регистрация: 03.07.2012 Сообщений: 8,228 Записей в блоге: 1 |
|
01.09.2014, 10:28 |
|
Можно в вики почитать про юникод. Вообще, по нему полно ресурсов, например кратко и популярно: http://zelserg.livejournal.com/2570.html
1 |
Tester64 420 / 357 / 47 Регистрация: 22.05.2013 Сообщений: 2,518 |
||||
01.09.2014, 18:06 [ТС] |
||||
Сообщение от Убежденный Windows уже лет 15 юникодная изнутри Не знаю с какой стороны она изнутри юникоидная… Но консоль осталась в 1251. Вроде читал где-то что это можно поменять — то-ли подменой шрифтов, то-ли шаманством в реестре. Но все программы которые хотят вывести в консоль кирилицу используют 1251. Включая bat-файлы. Попробуйте в Win bat-файл в юникоде кирилицу вставить:
Не уверен что после хака консоли даже стандартные команды вроде dir кирилистические названия файлов правильно выводить будут (сейчас выводят) А что такое юникод и чем он отличается от других кодировок, я думаю большинство и так знает. Но у него есть и свои минусы! По делфям помню (переводил проект с Delphi7 на Delphi2009) — каждый символ кодируется не одним байтом (как в других кодировках), от 2х до 4х!. Причем это плавающая величина и зависит от языка. И хранение в файлах и в памяти подобных строк увеличилось в 2-4 раза. Причем есть разные реализации юникода в разных ОС. Старые не поддерживали 4 а значит возможен глюк. Добавлено через 11 минут
0 |
DrOffset 19456 / 10069 / 2451 Регистрация: 30.01.2014 Сообщений: 17,749 |
||||
01.09.2014, 18:26 |
||||
Сообщение от Tester64 Не знаю с какой стороны она изнутри юникоидная… Windows юникодная изнутри. Консоль не юникодная по-умолчанию, и это сделано по всей видимости лишь для совместимости со старым ПО. Если мы пишем новое ПО нет никакой нужды подстраиваться под это. В VS например достаточно написать:
Чтобы перевести консоль в режим UTF16, соответственно, при наличии правильных шрифтов, wcout, wstring будут работать без каких-либо перекодировок. Сообщение от Tester64 Но консоль осталась в 1251 По-умолчанию она вообще в 866 кодировке (ДОС) в русской windows. Сообщение от Tester64 Слышал (активно не работал) что весь линукс работает в консоли и в основном написана на с/с++ Ну это не правда, что прям весь . Но консольные утилиты там гораздо лучше себя чувствуют, чем в windows, в том числе засчет развитой командной оболочки. Кстати в любом линуксе по-умолчанию используется кодировка юникода UTF-8.
0 |
4820 / 2286 / 287 Регистрация: 01.03.2013 Сообщений: 5,970 Записей в блоге: 30 |
|
01.09.2014, 23:23 |
|
Сообщение от gru74ik Ну и зачем стёр? Многим наверное было бы и полезно и интересно. Мне вот, например, интересно. +1. Мне тоже всегда интересно почитать имхи специалистов, тем более, если им можно потом еще задать вопрос. А вики мы в любом случае почитать можем.
1 |
Модератор 5287 / 2375 / 342 Регистрация: 20.02.2013 Сообщений: 5,773 Записей в блоге: 20 |
|
02.09.2014, 06:46 |
|
Сообщение от Tester64 Слышал (активно не работал) что весь линукс работает в консоли Там всё вполне себе цивилизованно — окошечки, менюшечки. Попробуй ради интереса Ubuntu поставить, к примеру. Посмотришь сам.
0 |
420 / 357 / 47 Регистрация: 22.05.2013 Сообщений: 2,518 |
|
02.09.2014, 17:36 [ТС] |
|
Сообщение от gru74ik Там всё вполне себе цивилизованно — окошечки, менюшечки. Попробуй ради интереса Ubuntu поставить, к примеру. Посмотришь сам «По приколу» делать это не хочется, а для работы не нужно (на 80% привязан к винде — остальное веб). Конечно раньше ставил (в виртуальные машины), даже где-то в коллекции лежит… Конечно там можно включить графику и работать только в ней. Но меня инетересует не это! Насколько сейчас активно кодят под консоль в С++? Нужна ли эта технология еще? Или давно замещена графикой? Конечно понимаю, что все сетевые технологии консольные, но кроме сетей?
0 |
19456 / 10069 / 2451 Регистрация: 30.01.2014 Сообщений: 17,749 |
|
02.09.2014, 18:17 |
|
Сообщение от Tester64 Насколько сейчас активно кодят под консоль в С++? Нет такого понятия «кодить под консоль».
1 |
Модератор 8532 / 3313 / 105 Регистрация: 24.05.2011 Сообщений: 14,492 Записей в блоге: 8 |
|
02.09.2014, 20:58 |
|
Сообщение от Tester64 весь линукс работает в консоли Я вас умоляю! Для повышения вашего уровня эрудиции в этом вопросе крайне рекомендую зайти хотя бы в Windows vs Linux (0Dh) или У кого как выглядит рабочий стол? (2), где вполне достаточно скринов рабстолов линукс
0 |
Optimus11 -41 / 49 / 5 Регистрация: 10.01.2017 Сообщений: 1,915 |
||||
05.11.2020, 14:09 |
||||
Сообщение от DrOffset Tester64, тут еще ведь нужно понимать, что L»строка» — это не UTF8. Это скорее UTF16 или USC2, если рассматривать windows.
Я немного запутался, разве MultiByteToWideChar — может конвертировать из UTF8 в CP1251 ? Добавлено через 5 минут А с точки зрения производительности — это ж двойные затраты получаются ? Может есть более быстрый способ конвертации между кодировками ?
0 |
raxper Эксперт 30234 / 6612 / 1498 Регистрация: 28.12.2010 Сообщений: 21,154 Блог |
05.11.2020, 14:09 |
20 |
Конвертирует строку из UTF-8 в Windows-1251
static string UTF8ToWin1251(string sourceStr)
{
Encoding utf8 = Encoding.UTF8;
Encoding win1251 = Encoding.GetEncoding(«Windows-1251»);
byte[] utf8Bytes = utf8.GetBytes(sourceStr);
byte[] win1251Bytes = Encoding.Convert(utf8, win1251, utf8Bytes);
return win1251.GetString(win1251Bytes);
}
Конвертирует строку из Windows-1251 в UTF-8
static private string Win1251ToUTF8(string source)
{
Encoding utf8 = Encoding.GetEncoding(«utf-8»);
Encoding win1251 = Encoding.GetEncoding(«windows-1251»);
byte[] utf8Bytes = win1251.GetBytes(source);
byte[] win1251Bytes = Encoding.Convert(win1251, utf8, utf8Bytes);
source = win1251.GetString(win1251Bytes);
return source;
}
Welcome to our comprehensive guide on Windows-1251 encoding in Java! If you’re a developer looking to understand character encoding and how to effectively handle Cyrillic text in your Java applications, you’re in the right place. This page will provide you with essential insights into the Windows-1251 encoding standard, its importance for processing text in languages like Russian, and practical examples of how to implement it in your Java code. Whether you’re troubleshooting encoding issues or seeking to enhance your software’s internationalization capabilities, you’ll find valuable tips and techniques to elevate your programming skills. Let’s dive into the world of Windows-1251 encoding and unlock the potential of Java for multilingual applications!
Introduction to Windows-1251
Windows-1251 is a character encoding standard developed by Microsoft for the representation of Cyrillic scripts. It was designed to accommodate languages that use the Cyrillic alphabet, including Russian, Ukrainian, and Bulgarian. As a single-byte character encoding, Windows-1251 can represent 256 different characters, making it a popular choice for applications dealing with Eastern European languages. Despite the growing adoption of Unicode, Windows-1251 remains relevant in legacy systems and specific applications that require Cyrillic text processing.
In Java, encoding text with Windows-1251 is straightforward. The Java platform provides built-in support for various character encodings, including Windows-1251. To encode a string into a byte array using Windows-1251, you can use the getBytes
method of the String
class, specifying the encoding as an argument. Here’s an example:
import java.nio.charset.Charset;
public class EncodeExample {
public static void main(String[] args) {
String text = "Привет, мир!"; // "Hello, World!" in Russian
byte[] encodedBytes = text.getBytes(Charset.forName("Windows-1251"));
// Print the encoded byte array
System.out.println("Encoded bytes: " + java.util.Arrays.toString(encodedBytes));
}
}
This code snippet demonstrates how to convert a string containing Cyrillic characters into its Windows-1251 encoded byte representation. It’s essential to use the correct character set to avoid data corruption.
Decoding with Windows-1251 in Java
Decoding text encoded in Windows-1251 back into a Java String
is equally simple. The String
constructor can be utilized, which takes a byte array and the desired charset as parameters. Here’s how you can decode Windows-1251 encoded data:
import java.nio.charset.Charset;
public class DecodeExample {
public static void main(String[] args) {
byte[] encodedBytes = { -24, -112, -108, -24, -111, -100, -24, -113, -101, -24, -112, -116 }; // Example byte array
String decodedText = new String(encodedBytes, Charset.forName("Windows-1251"));
// Print the decoded string
System.out.println("Decoded text: " + decodedText);
}
}
In this example, we convert a byte array back into a string using Windows-1251 encoding. It’s crucial to ensure the byte array accurately represents the original text; otherwise, the output may contain garbled characters.
Advantages and Disadvantages of Windows-1251
Advantages
- Simplicity: Windows-1251 is easy to implement, especially in legacy systems where the character set is well-defined.
- Efficiency: Being a single-byte encoding, it can be more memory-efficient for applications that primarily deal with Cyrillic text compared to multi-byte encodings like UTF-8.
Disadvantages
- Limited Character Set: Windows-1251 only supports Cyrillic characters, which can be limiting for applications that require multilingual support.
- Obsolescence: As the Unicode standard gains traction, Windows-1251 is gradually becoming less common, leading to potential compatibility issues in modern applications.
Key Applications of Windows-1251
Windows-1251 is commonly used in various applications, particularly those involving legacy systems or specific Eastern European contexts. Key applications include:
- Text Processing: Software that processes Cyrillic text, such as word processors and text editors, often utilizes Windows-1251 encoding.
- Databases: Some databases may still store data in Windows-1251, especially if they were developed before the widespread adoption of Unicode.
- Web Development: Older websites that cater to Russian or other Cyrillic language audiences may still use Windows-1251 encoding for their content.
Popular Frameworks and Tools for Windows-1251
Several frameworks and tools support Windows-1251 encoding, making it easier for developers to work with Cyrillic text. Some of the most popular include:
- Apache Commons Text: This library provides utilities for encoding and decoding various character sets, including Windows-1251.
- Java’s Built-in Libraries: The standard Java libraries offer robust support for Windows-1251 through the
Charset
class, enabling seamless encoding and decoding. - Spring Framework: This popular Java framework supports various character encodings, allowing developers to easily integrate Windows-1251 in web applications.
In conclusion, while Windows-1251 may not be the most modern encoding standard, it still holds significance in specific use cases, especially when dealing with Cyrillic text in Java applications. Understanding how to encode and decode using this standard is essential for developers working in Eastern European contexts.
Для конвертации на php строки из utf-8 в windows-1251 и наоборот, можно использовать следующую функцию:
Описание функции iconv:
string iconv ( string from_kodirovka, string to_kodirovka, string str )
Производит преобразование кодировки символов строки str из начальной кодировки from_kodirovka в конечную to_kodirovka. Возвращает строку в новой кодировке, или FALSE в случае ошибки.
Если добавить //TRANSLIT к параметру out_charset будет включена транслитеризация. Это означает, что вслучае, когда символа нет в конечной кодировке, он заменяется одним или несколькими аналогами. Если добавить //IGNORE, то символы, которых нет в конечной кодировке, будут опущены. Иначе, будет возвращена строка str, обрезанная до первого недопустимого символа.
В случае, если ваш хостинг не поддерживает iconv, для конвертации из utf-8 в win-1251 и наоборот можно использовать следующие функции:
function utf8_to_cp1251($s) { $tbl = $GLOBALS['unicode_to_cp1251_tbl']; $uc = 0; $bits = 0; $r = ""; for($i = 0, $l = strlen($s); $i < $l; $i++) { $c = $s{$i}; $b = ord($c); if($b & 0x80) { if($b & 0x40) { if($b & 0x20) { $uc = ($b & 0x0F) << 12; $bits = 12; } else { $uc = ($b & 0x1F) << 6; $bits = 6; } } else { $bits -= 6; if($bits) { $uc |= ($b & 0x3F) << $bits; } else { $uc |= $b & 0x3F; if($cc = @$tbl[$uc]) { $r .= $cc; } else { $r .= '?'; } } } } else { $r .= $c; } } return $r; }
function cp1251_to_utf8($s) { $tbl = $GLOBALS['cp1251_to_utf8_tbl']; $r = ""; for($i = 0, $l = strlen($s); $i < $l; $i++) { $c = $s{$i}; $b = ord($c); if ($b < 128) { $r .= $c; } else { $r .= @$tbl[$b]; } } return $r; } $unicode_to_cp1251_tbl = array( 0x0402 => "\x80", 0x0403 => "\x81", 0x201A => "\x82", 0x0453 => "\x83", 0x201E => "\x84", 0x2026 => "\x85", 0x2020 => "\x86", 0x2021 => "\x87", 0x20AC => "\x88", 0x2030 => "\x89", 0x0409 => "\x8A", 0x2039 => "\x8B", 0x040A => "\x8C", 0x040C => "\x8D", 0x040B => "\x8E", 0x040F => "\x8F", 0x0452 => "\x90", 0x2018 => "\x91", 0x2019 => "\x92", 0x201C => "\x93", 0x201D => "\x94", 0x2022 => "\x95", 0x2013 => "\x96", 0x2014 => "\x97", 0x2122 => "\x99", 0x0459 => "\x9A", 0x203A => "\x9B", 0x045A => "\x9C", 0x045C => "\x9D", 0x045B => "\x9E", 0x045F => "\x9F", 0x00A0 => "\xA0", 0x040E => "\xA1", 0x045E => "\xA2", 0x0408 => "\xA3", 0x00A4 => "\xA4", 0x0490 => "\xA5", 0x00A6 => "\xA6", 0x00A7 => "\xA7", 0x0401 => "\xA8", 0x00A9 => "\xA9", 0x0404 => "\xAA", 0x00AB => "\xAB", 0x00AC => "\xAC", 0x00AD => "\xAD", 0x00AE => "\xAE", 0x0407 => "\xAF", 0x00B0 => "\xB0", 0x00B1 => "\xB1", 0x0406 => "\xB2", 0x0456 => "\xB3", 0x0491 => "\xB4", 0x00B5 => "\xB5", 0x00B6 => "\xB6", 0x00B7 => "\xB7", 0x0451 => "\xB8", 0x2116 => "\xB9", 0x0454 => "\xBA", 0x00BB => "\xBB", 0x0458 => "\xBC", 0x0405 => "\xBD", 0x0455 => "\xBE", 0x0457 => "\xBF", 0x0410 => "\xC0", 0x0411 => "\xC1", 0x0412 => "\xC2", 0x0413 => "\xC3", 0x0414 => "\xC4", 0x0415 => "\xC5", 0x0416 => "\xC6", 0x0417 => "\xC7", 0x0418 => "\xC8", 0x0419 => "\xC9", 0x041A => "\xCA", 0x041B => "\xCB", 0x041C => "\xCC", 0x041D => "\xCD", 0x041E => "\xCE", 0x041F => "\xCF", 0x0420 => "\xD0", 0x0421 => "\xD1", 0x0422 => "\xD2", 0x0423 => "\xD3", 0x0424 => "\xD4", 0x0425 => "\xD5", 0x0426 => "\xD6", 0x0427 => "\xD7", 0x0428 => "\xD8", 0x0429 => "\xD9", 0x042A => "\xDA", 0x042B => "\xDB", 0x042C => "\xDC", 0x042D => "\xDD", 0x042E => "\xDE", 0x042F => "\xDF", 0x0430 => "\xE0", 0x0431 => "\xE1", 0x0432 => "\xE2", 0x0433 => "\xE3", 0x0434 => "\xE4", 0x0435 => "\xE5", 0x0436 => "\xE6", 0x0437 => "\xE7", 0x0438 => "\xE8", 0x0439 => "\xE9", 0x043A => "\xEA", 0x043B => "\xEB", 0x043C => "\xEC", 0x043D => "\xED", 0x043E => "\xEE", 0x043F => "\xEF", 0x0440 => "\xF0", 0x0441 => "\xF1", 0x0442 => "\xF2", 0x0443 => "\xF3", 0x0444 => "\xF4", 0x0445 => "\xF5", 0x0446 => "\xF6", 0x0447 => "\xF7", 0x0448 => "\xF8", 0x0449 => "\xF9", 0x044A => "\xFA", 0x044B => "\xFB", 0x044C => "\xFC", 0x044D => "\xFD", 0x044E => "\xFE", 0x044F => "\xFF", ); $cp1251_to_utf8_tbl = array( 0x80 => "\xD0\x82", 0x81 => "\xD0\x83", 0x82 => "\xE2\x80\x9A", 0x83 => "\xD1\x93", 0x84 => "\xE2\x80\x9E", 0x85 => "\xE2\x80\xA6", 0x86 => "\xE2\x80\xA0", 0x87 => "\xE2\x80\xA1", 0x88 => "\xE2\x82\xAC", 0x89 => "\xE2\x80\xB0", 0x8A => "\xD0\x89", 0x8B => "\xE2\x80\xB9", 0x8C => "\xD0\x8A", 0x8D => "\xD0\x8C", 0x8E => "\xD0\x8B", 0x8F => "\xD0\x8F", 0x90 => "\xD1\x92", 0x91 => "\xE2\x80\x98", 0x92 => "\xE2\x80\x99", 0x93 => "\xE2\x80\x9C", 0x94 => "\xE2\x80\x9D", 0x95 => "\xE2\x80\xA2", 0x96 => "\xE2\x80\x93", 0x97 => "\xE2\x80\x94", 0x99 => "\xE2\x84\xA2", 0x9A => "\xD1\x99", 0x9B => "\xE2\x80\xBA", 0x9C => "\xD1\x9A", 0x9D => "\xD1\x9C", 0x9E => "\xD1\x9B", 0x9F => "\xD1\x9F", 0xA0 => "\xC2\xA0", 0xA1 => "\xD0\x8E", 0xA2 => "\xD1\x9E", 0xA3 => "\xD0\x88", 0xA4 => "\xC2\xA4", 0xA5 => "\xD2\x90", 0xA6 => "\xC2\xA6", 0xA7 => "\xC2\xA7", 0xA8 => "\xD0\x81", 0xA9 => "\xC2\xA9", 0xAA => "\xD0\x84", 0xAB => "\xC2\xAB", 0xAC => "\xC2\xAC", 0xAD => "\xC2\xAD", 0xAE => "\xC2\xAE", 0xAF => "\xD0\x87", 0xB0 => "\xC2\xB0", 0xB1 => "\xC2\xB1", 0xB2 => "\xD0\x86", 0xB3 => "\xD1\x96", 0xB4 => "\xD2\x91", 0xB5 => "\xC2\xB5", 0xB6 => "\xC2\xB6", 0xB7 => "\xC2\xB7", 0xB8 => "\xD1\x91", 0xB9 => "\xE2\x84\x96", 0xBA => "\xD1\x94", 0xBB => "\xC2\xBB", 0xBC => "\xD1\x98", 0xBD => "\xD0\x85", 0xBE => "\xD1\x95", 0xBF => "\xD1\x97", 0xC0 => "\xD0\x90", 0xC1 => "\xD0\x91", 0xC2 => "\xD0\x92", 0xC3 => "\xD0\x93", 0xC4 => "\xD0\x94", 0xC5 => "\xD0\x95", 0xC6 => "\xD0\x96", 0xC7 => "\xD0\x97", 0xC8 => "\xD0\x98", 0xC9 => "\xD0\x99", 0xCA => "\xD0\x9A", 0xCB => "\xD0\x9B", 0xCC => "\xD0\x9C", 0xCD => "\xD0\x9D", 0xCE => "\xD0\x9E", 0xCF => "\xD0\x9F", 0xD0 => "\xD0\xA0", 0xD1 => "\xD0\xA1", 0xD2 => "\xD0\xA2", 0xD3 => "\xD0\xA3", 0xD4 => "\xD0\xA4", 0xD5 => "\xD0\xA5", 0xD6 => "\xD0\xA6", 0xD7 => "\xD0\xA7", 0xD8 => "\xD0\xA8", 0xD9 => "\xD0\xA9", 0xDA => "\xD0\xAA", 0xDB => "\xD0\xAB", 0xDC => "\xD0\xAC", 0xDD => "\xD0\xAD", 0xDE => "\xD0\xAE", 0xDF => "\xD0\xAF", 0xE0 => "\xD0\xB0", 0xE1 => "\xD0\xB1", 0xE2 => "\xD0\xB2", 0xE3 => "\xD0\xB3", 0xE4 => "\xD0\xB4", 0xE5 => "\xD0\xB5", 0xE6 => "\xD0\xB6", 0xE7 => "\xD0\xB7", 0xE8 => "\xD0\xB8", 0xE9 => "\xD0\xB9", 0xEA => "\xD0\xBA", 0xEB => "\xD0\xBB", 0xEC => "\xD0\xBC", 0xED => "\xD0\xBD", 0xEE => "\xD0\xBE", 0xEF => "\xD0\xBF", 0xF0 => "\xD1\x80", 0xF1 => "\xD1\x81", 0xF2 => "\xD1\x82", 0xF3 => "\xD1\x83", 0xF4 => "\xD1\x84", 0xF5 => "\xD1\x85", 0xF6 => "\xD1\x86", 0xF7 => "\xD1\x87", 0xF8 => "\xD1\x88", 0xF9 => "\xD1\x89", 0xFA => "\xD1\x8A", 0xFB => "\xD1\x8B", 0xFC => "\xD1\x8C", 0xFD => "\xD1\x8D", 0xFE => "\xD1\x8E", 0xFF => "\xD1\x8F", );
REPA
Функция на языке Си для конвертации строк из кодировки UTF-8 в Windows-1251 (CP1251)
Файл с функцией: https://github.com/0x1801/REPA/blob/main/utf8_2_win1251.c
- Поставляется в виде исходного кода.
- Написана на языке С.
- Может быть использована в программах на языке C++.
- Может применяться в программах для микроконтроллеров
- Не использует ни SIMD-инструкций, ни даже x64.
- Использует очень мало памяти: 1 массив на 32 байта (компилятор кладет его в векторный регистр, если он есть) + несколько констант.
- Поддерживает символы utf8 до 4х байт (стандарт RFC 3629)
- Входной массив может совпадать с выходным: данные будут перезаписаны.
Применение:
Вам ничего не понадобится, кроме текста функции и 3х макросов перед ней. Ни инклюдов и библиотек, ни массивов, никакого другого кода. Просто скопируйте ее в свой проект.
ВНИМАНИЕ: Функция требует наличия 2х лишних выделенных байтов памяти за символом конца строки во входном массиве с символами utf8. В этих байтах может лежать любой мусор. Обычно, если в вашем проекте код написан оптимально, то вы не будете каждый раз выделять память под строку. Поэтому выделить 2 лишних байта — это не проблема. Но если в вашем проекте сложно это внедрить, то можете немного самостоятельно модифицировать код.
Если есть желание проверить работу функции, можно написать тест самостоятельно или воспользоваться заготовкой из main.c: https://github.com/0x1801/REPA/blob/main/main.c
Больше main.c ни для чего не нужен.
БОНУС: в файле https://github.com/0x1801/REPA/blob/main/koi8r_2_windows1251_AVX512.c можно найти функцию конвертации из любой 8-битной ASCII-совместимой кодировки в любую 8-битную ASCII-совместимую кодировку, написанную с использованием векторных инструкций AVX512. В коде для примера реализована конвертация из koi8r в windows 1251, но алгоритм пригоден для конвертации любоых сочетаний 8-битных кодировок, совместимых с ASCII. Признаюсь честно, что сам я ее тестировать поленился, т.к. msvc 2015 «из коробки» не знает функций, которые я использовал. Функция, как минимум, компилируется (в коментарии к ней ссылка на godbolt.org). Просто мне было интересно написать функцию, которая умеет конвертировать сразу 64 символа всего за 12 инструкций (само отображение занимает при этом вообще 2 инструкции). Если вам удастся протестировать функцию или найти в ней ошибки (или улучшения), напишите мне, пожалуйста.
Связаться с автором:
Илья
chronosphere@mail.ru.