乡下人产国偷v产偷v自拍,国产午夜片在线观看,婷婷成人亚洲综合国产麻豆,久久综合给合久久狠狠狠9

  • <output id="e9wm2"></output>
    <s id="e9wm2"><nobr id="e9wm2"><ins id="e9wm2"></ins></nobr></s>

    • 分享

      C++11與Unicode及使用標(biāo)準(zhǔn)庫(kù)進(jìn)行UTF

       鳳凰苑兇真 2019-02-12

      Unicode

      Unicode是計(jì)算機(jī)領(lǐng)域的一項(xiàng)行業(yè)標(biāo)準(zhǔn),它對(duì)世界上絕大部分的文字的進(jìn)行整理和統(tǒng)一編碼,Unicode的編碼空間可以劃分為17個(gè)平面(plane),每個(gè)平面包含2的16次方(65536)個(gè)碼位。17個(gè)平面的碼位可表示為從U+0000到U+10FFFF,共計(jì)1114112個(gè)碼位,第一個(gè)平面稱為基本多語(yǔ)言平面(Basic Multilingual Plane, BMP),或稱第零平面(Plane 0)。其他平面稱為輔助平面(Supplementary Planes)。基本多語(yǔ)言平面內(nèi),從U+D800到U+DFFF之間的碼位區(qū)段是永久保留不映射到Unicode字符,所以有效碼位為1112064個(gè)。最新的版本是Unicode 6.3發(fā)布于2013年9月30日。

      Unicode的編碼方式

      對(duì)于被Unicode收錄的字符其編碼是唯一且確定的。但是Unicode的實(shí)現(xiàn)方式(出于傳輸、存儲(chǔ)、處理或向后兼容的考慮)卻有不同的幾種,其中最流行的是UTF-8、UTF-16、UCS2、UCS4/UTF-32等,細(xì)分的話還有大小端的區(qū)別。

      UTF-8(8-bit Unicode Transformation Format)

      UTF-8是一種變長(zhǎng)編碼,對(duì)于一個(gè)Unicode的字符被編碼成1至4個(gè)字節(jié)。Unicode編碼與UTF-8的編碼的對(duì)應(yīng)關(guān)系如下表

      Unicode編碼 UTF-8編碼(二進(jìn)制)
      U+0000 – U+007F 0xxxxxxx
      U+0080 – U+07FF 110xxxxx 10xxxxxx
      U+0800 – U+FFFF 1110xxxx 10xxxxxx 10xxxxxx
      U+10000 – U+10FFFF 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx

      其中絕大部分的中文用三個(gè)字節(jié)編碼,部分中文用四個(gè)字節(jié)編碼,舉例如下:

      Unicode 字符 UTF-8編碼
      U+0041 A 0x41
      U+7834 0xE7 0xA0 0xB4
      U+6653 0xE6 0x99 0x93
      U+2A6A5 ??(四個(gè)龍) 0xF0 0xAA 0x9A 0xA5

      優(yōu)點(diǎn):

      1. 向后兼容ASCII編碼;
      2. 沒(méi)有字節(jié)序(大小端)的問(wèn)題適合網(wǎng)絡(luò)傳輸;
      3. 存儲(chǔ)英文和拉丁文等字符非常節(jié)省存儲(chǔ)空間。

      缺點(diǎn):

      1. 變長(zhǎng)編碼不利于文本處理;
      2. 對(duì)于CJK等文字比較浪費(fèi)存儲(chǔ)空間。

      UTF-16(16-bit Unicode Transformation Format)

      UTF-16也是一種變長(zhǎng)編碼,對(duì)于一個(gè)Unicode字符被編碼成1至2個(gè)碼元,每個(gè)碼元為16位。

      基本多語(yǔ)言平面(碼位范圍U+0000-U+FFFF)

      在基本多語(yǔ)言平面內(nèi)的碼位UTF-16編碼使用1個(gè)碼元且其值與Unicode是相等的(不需要轉(zhuǎn)換)。舉例如下

      Unicode 字符 UTF-16(碼元) UTF-16 LE(字節(jié)) UTF-16 BE(字節(jié))
      U+0041 A 0x0041 0x41 0x00 0x00 0x41
      U+7834 0x7834 0x34 0x78 0x78 0x34
      U+6653 0x6653 0x53 0x66 0x66 0x53

      輔助平面(碼位范圍U+10000-U+10FFFF)

      在輔助平面內(nèi)的碼位在UTF-16中被編碼為一對(duì)16bit的碼元(即32bit,4字節(jié)),稱作代理對(duì)(surrogate pair)。組成代理對(duì)的兩個(gè)碼元前一個(gè)稱為前導(dǎo)代理(lead surrogates)范圍為0xD800-0xDBFF,后一個(gè)稱為后尾代理(trail surrogates)范圍為0xDC00-0xDFFF。UTF-16輔助平面代理對(duì)與Unicode的對(duì)應(yīng)關(guān)系如下表

      Lead \ Trail 0xDC00 0xDC01 0xDFFF
      0xD800 U+10000 U+10001 U+103FF
      0xD801 U+10400 U+10401 U+107FF
      ? ? ? ? ?
      0xDBFF U+10FC00 U+10FC01 U+10FFFF

      舉例如下

      Unicode 字符 UTF-16(碼元) UTF-16 LE(字節(jié)) UTF-16 BE(字節(jié))
      U+2A6A5 ?? 0xD869 0xDEA5 0x69 0xD8 0xA5 0xDE 0xD8 0x69 0xDE 0xA5

      優(yōu)點(diǎn):

      1. 絕大部分的文字都可以用兩個(gè)字節(jié)編碼,對(duì)于CJK文字是比較節(jié)省空間的;
      2. 文本處理比UTF-8方便得多。

      缺點(diǎn):

      1. 存儲(chǔ)和傳輸需要考慮字節(jié)序的問(wèn)題;
      2. 不兼容ASCII。

      UCS2(2-byte Universal Character Set)

      UCS2是一種定長(zhǎng)編碼,編碼范圍為0x0000-0xFFFF。在基本多語(yǔ)言平面內(nèi)與UTF-16是等價(jià)。UCS2沒(méi)有類似于UTF-16中代理對(duì)的概念,所以對(duì)于0xD869 0xDEA5會(huì)識(shí)別成兩個(gè)字符。因?yàn)槭嵌ㄩL(zhǎng)編碼,所以文本處理很方便。缺點(diǎn)是不能表示全部的Unicode字符。

      UCS4(4-byte Universal Character Set)/UTF-32(32-bit Unicode Transformation Format)

      UCS4/UTF-32是一種定長(zhǎng)編碼,使用1個(gè)32bit的碼元,其值與Unicode編碼值相等。舉例如下:

      Unicode 字符 UTF-32(碼元) UTF-32 LE(字節(jié)) UTF-32 BE(字節(jié))
      U+0041 A 0x00000041 0x41 0x00 0x00 0x00 0x00 0x00 0x00 0x41
      U+7834 0x00007834 0x34 0x78 0x00 0x00 0x00 0x00 0x78 0x34
      U+6653 0x00006653 0x53 0x66 0x00 0x00 0x00 0x00 0x66 0x53
      U+2A6A5 ?? 0x0002A6A5 0xA5 0xA6 0x02 0x00 0x00 0x02 0xA6 0xA5

      優(yōu)點(diǎn)是編碼定長(zhǎng)容易進(jìn)行文本處理,缺點(diǎn)是浪費(fèi)存儲(chǔ)空間及存在字節(jié)序的問(wèn)題。

      C++11對(duì)Unicode的支持

      C++11對(duì)Unicode提供了語(yǔ)言級(jí)別和庫(kù)級(jí)別的支持。

      USL(Unicode String Literals)

      USL是C++11對(duì)Unicode提供的語(yǔ)言級(jí)別的支持。在C++11之前C++中有個(gè)wchar_t的類型用于存儲(chǔ)寬字符(Wide-Character)。你可以寫下面這樣的代碼

      1
      2
      3
      wchar_t wc = L'中';
      wchar_t wc_array[] = L"破曉的博客";
      std::wstring wstr = L"破曉的博客";

      以L開(kāi)頭的字符(或字符串)字面量稱為WCSL(Wide-Character String Literals)。本意大概也是用來(lái)提供Unicode支持的,可惜標(biāo)準(zhǔn)沒(méi)有規(guī)定這個(gè)的實(shí)現(xiàn),wchar_t及其字面量是實(shí)現(xiàn)相關(guān)的。比如

      1. 在windows平臺(tái)下sizeof(wchar_t)為2,而在linux平臺(tái)下sizeof(wchar_t)為4;
      2. 在windows平臺(tái)下寬字符(或字符串)字面量使用UTF-16編碼,linux平臺(tái)下使用UTF-32編碼。

      這導(dǎo)致了下面這段代碼在windows下編譯時(shí)會(huì)報(bào)錯(cuò),而在linux下可以編譯通過(guò)。

      1
      wchar_t wc = L'??'; // U+2A6A5

      C++11新增了char16_t(至少16位)和char32_t(至少32位)以及USL允許下面這樣的代碼

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      // utf-8
      char u8_array[] = u8"破曉的博客";
      std::string u8_str = u8"破曉的博客";
      // utf-16
      char16_t u16_c = u'中';
      char16_t u16_array[] = u"破曉的博客";
      std::u16string u16_str = u"破曉的博客";
      // ucs4
      char32_t u32_c = U'??';
      char32_t u32_array[] = U"破曉的博客";
      std::u32string u32_str = U"破曉的博客";

      上面在字符(或字符串)字面量前面的u8、u及U前綴分別表示這是UTF-8、UTF-16和UCS4編碼的字符(或字符串)字面量,用法與L前綴類似。下面是一段測(cè)試代碼,print_code_uint_sequence函數(shù)模板用于輸出字符串的碼元序列。

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      17
      18
      19
      20
      21
      22
      23
      24
      25
      26
      27
      28
      29
      30
      31
      32
      33
      34
      #include <string>
      #include <iostream>
      #include <iomanip>
      #include <type_traits>

      template<typename tStringType, typename tTraits = typename tStringType::traits_type>
      void print_code_unit_sequence(tStringType str)
      {
      using char_type = typename tTraits::char_type;
      static_assert(std::is_same<char_type, char>::value || std::is_same<char_type, char16_t>::value || std::is_same<char_type, char32_t>::value, "error");
      using unsigned_char_type = typename std::make_unsigned<char_type>::type;
      using unsigned_int_type = typename std::make_unsigned<typename tTraits::int_type>::type;
      int w = std::is_same<char, char_type>::value ? 2 : std::is_same<char16_t, char_type>::value ? 4 : 8;
      for(auto c : str) {
      auto value = static_cast<unsigned_int_type>(static_cast<unsigned_char_type>(c));
      std::cout << "0x" << std::hex << std::uppercase << std::setw(w) << std::setfill('0') << value << ' ';
      }
      }

      int main()
      {
      std::string u8_str = u8"??"; // utf-8
      std::u16string u16_str = u"??"; // utf-16
      std::u32string u32_str = U"??"; // ucs4
      std::cout << "utf-8: ";
      print_code_unit_sequence(u8_str);
      std::cout << std::endl;
      std::cout << "utf-16: ";
      print_code_unit_sequence(u16_str);
      std::cout << std::endl;
      std::cout << "ucs4: ";
      print_code_unit_sequence(u32_str);
      std::cout << std::endl;
      }

      輸出

      1
      2
      3
      utf-8: 0xF0 0xAA 0x9A 0xA5
      utf-16: 0xD869 0xDEA5
      ucs4: 0x0002A6A5

      使用C++11標(biāo)準(zhǔn)庫(kù)進(jìn)行編碼轉(zhuǎn)換

      C++11標(biāo)準(zhǔn)庫(kù)在<codecvt>頭文件中定義了3個(gè)Unicode編碼轉(zhuǎn)換的Facet

      Facet 說(shuō)明
      std::codecvt_utf8 封裝了UTF-8與UCS2及UTF-8與UCS4的編碼轉(zhuǎn)換
      std::codecvt_utf16 封裝了UTF-16與UCS2及UTF-16與UCS4的編碼轉(zhuǎn)換
      std::codecvt_utf8_utf16 封裝了UTF-8與UTF-16的編碼轉(zhuǎn)換

      當(dāng)要轉(zhuǎn)換的字符串為std::basic_string使用<locale>頭文件中定義的std::wstring_convert類模板會(huì)帶來(lái)極大的方便。

      1
      2
      3
      4
      5
      template<class Codecvt,
      class Elem = wchar_t,
      class Wide_alloc = std::allocator<Elem>,
      class Byte_alloc = std::allocator<char>>
      class wstring_convert;

      UTF-8與UTF-16編碼轉(zhuǎn)換

      UTF-8與UTF-16的編碼轉(zhuǎn)換使用std::codecvt_utf8_utf16類模板

      1
      2
      3
      4
      template<class Elem,
      unsigned long Maxcode = 0x10ffff,
      std::codecvt_mode Mode = (std::codecvt_mode)0>
      class codecvt_utf8_utf16 : public std::codecvt<Elem, char, std::mbstate_t>;

      其中Elem用于存儲(chǔ)UTF-16碼元,可以是char16_t、char32_t或wchar_t(這些類型都至少能夠存儲(chǔ)16bit)。下面的代碼演示了UTF-8到UTF-16和UTF-16到UTF-8的編碼轉(zhuǎn)換

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      std::string u8_source_str = u8"破曉的博客"; // utf-8
      std::wstring_convert<std::codecvt_utf8_utf16<char16_t>, char16_t> cvt;
      std::u16string u16_cvt_str = cvt.from_bytes(u8_source_str); // utf-8 to utf-16
      std::string u8_cvt_str = cvt.to_bytes(u16_cvt_str); // utf-16 to utf-8
      std::cout << "u8_source_str = ";
      print_code_unit_sequence(u8_source_str);
      std::cout << std::endl;
      std::cout << "u16_cvt_str = ";
      print_code_unit_sequence(u16_cvt_str);
      std::cout << std::endl;
      std::cout << "u8_cvt_str = ";
      print_code_unit_sequence(u8_cvt_str);
      std::cout << std::endl;

      輸出

      1
      2
      3
      u8_source_str = 0xE7 0xA0 0xB4 0xE6 0x99 0x93 0xE7 0x9A 0x84 0xE5 0x8D 0x9A 0xE5 0xAE 0xA2
      u16_cvt_str = 0x7834 0x6653 0x7684 0x535A 0x5BA2
      u8_cvt_str = 0xE7 0xA0 0xB4 0xE6 0x99 0x93 0xE7 0x9A 0x84 0xE5 0x8D 0x9A 0xE5 0xAE 0xA2

      UTF-8與UCS2編碼轉(zhuǎn)換及UTF-8與UCS4編碼轉(zhuǎn)換

      UTF-8與UCS2或UCS4編碼轉(zhuǎn)換使用std::codecvt_utf8類模板

      1
      2
      3
      4
      template<class Elem,
      unsigned long Maxcode = 0x10ffff,
      std::codecvt_mode Mode = (std::codecvt_mode)0>
      class codecvt_utf8 : public std::codecvt<Elem, char, std::mbstate_t>;

      當(dāng)Elem為char16_t時(shí)轉(zhuǎn)換為UTF-8與UCS2,當(dāng)Elem為char32_t時(shí)轉(zhuǎn)換為UTF-16與UCS4,當(dāng)Elem為wchar_t時(shí)轉(zhuǎn)換取決于實(shí)現(xiàn)。演示如下

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      17
      18
      19
      20
      21
      22
      std::string u8_source_str = u8"破曉的博客"; // utf-8
      std::wstring_convert<std::codecvt_utf8<char16_t>, char16_t> utf8_ucs2_cvt;
      std::u16string ucs2_cvt_str = utf8_ucs2_cvt.from_bytes(u8_source_str); // utf-8 to ucs2
      std::string u8_str_from_ucs2 = utf8_ucs2_cvt.to_bytes(ucs2_cvt_str); // ucs2 to utf-8
      std::wstring_convert<std::codecvt_utf8<char32_t>, char32_t> utf8_ucs4_cvt;
      std::u32string ucs4_cvt_str = utf8_ucs4_cvt.from_bytes(u8_source_str); // utf-8 to ucs4
      std::string u8_str_from_ucs4 = utf8_ucs4_cvt.to_bytes(ucs4_cvt_str); // ucs4 to utf-8
      std::cout << "u8_source_str: ";
      print_code_unit_sequence(u8_source_str);
      std::cout << std::endl;
      std::cout << "ucs2_cvt_str: ";
      print_code_unit_sequence(ucs2_cvt_str);
      std::cout << std::endl;
      std::cout << "u8_str_from_ucs2: ";
      print_code_unit_sequence(u8_str_from_ucs2);
      std::cout << std::endl;
      std::cout << "ucs4_cvt_str: ";
      print_code_unit_sequence(ucs4_cvt_str);
      std::cout << std::endl;
      std::cout << "u8_str_from_ucs4: ";
      print_code_unit_sequence(u8_str_from_ucs4);
      std::cout << std::endl;

      輸出

      1
      2
      3
      4
      5
      u8_source_str: 0xE7 0xA0 0xB4 0xE6 0x99 0x93 0xE7 0x9A 0x84 0xE5 0x8D 0x9A 0xE5 0xAE 0xA2
      ucs2_cvt_str: 0x7834 0x6653 0x7684 0x535A 0x5BA2
      u8_str_from_ucs2: 0xE7 0xA0 0xB4 0xE6 0x99 0x93 0xE7 0x9A 0x84 0xE5 0x8D 0x9A 0xE5 0xAE 0xA2
      ucs4_cvt_str: 0x00007834 0x00006653 0x00007684 0x0000535A 0x00005BA2
      u8_str_from_ucs4: 0xE7 0xA0 0xB4 0xE6 0x99 0x93 0xE7 0x9A 0x84 0xE5 0x8D 0x9A 0xE5 0xAE 0xA2

      與UCS2進(jìn)行轉(zhuǎn)換時(shí)需要注意的是,由于UCS2不能表示全部Unicode,所以當(dāng)向UCS2轉(zhuǎn)換時(shí)UCS2無(wú)法表示時(shí)會(huì)拋出std::range_error異常。

      UTF-16與UCS2編碼轉(zhuǎn)換及UTF-16與UCS4編碼轉(zhuǎn)換

      UTF-16轉(zhuǎn)UCS2或UCS4使用std::codecvt_utf16類模板

      1
      2
      3
      4
      template<class Elem,
      unsigned long Maxcode = 0x10ffff,
      std::codecvt_mode Mode = (std::codecvt_mode)0>
      class codecvt_utf16 : public std::codecvt<Elem, char, std::mbstate_t>;

      這里以UTF-16與UCS4的轉(zhuǎn)換為例Elem為char32_t,UTF-16與UCS2的轉(zhuǎn)換類似只是Elem需為char16_t。
      由于std::wstring_convert是用于在byte string和wide string之間轉(zhuǎn)換,使用std::codecvt_utf16時(shí)UTF-16字符串作為byte string,因此使用這個(gè)轉(zhuǎn)換時(shí)就需要考慮字節(jié)序的問(wèn)題。std::codecvt_utf16類模板的第3個(gè)模板參數(shù)Mode類型為std::codecvt_mode

      1
      2
      3
      4
      5
      enum codecvt_mode {
      consume_header = 4,
      generate_header = 2,
      little_endian = 1
      };

      這三個(gè)枚舉值的含義如下表

      枚舉值 描述
      consume_header 告訴codecvt需要處理輸入的byte string中的BOM(Byte Order Mark)
      generate_header 告訴codecvt在輸出的byte string中添加BOM
      little_endian 告訴codecvt將byte string的字節(jié)序視為小端(Little Endian),默認(rèn)為大端(Big Endian)

      下面的代碼演示了UTF-16 BE和UTF-16 LE編碼到UCS4編碼的轉(zhuǎn)換

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      17
      18
      std::string u16le_byte_str = "\x34\x78\x53\x66"; // utf-16 Little Endian
      std::string u16be_byte_str = "\x78\x34\x66\x53"; // utf-16 Big Endian
      std::wstring_convert<std::codecvt_utf16<char32_t, 0x10ffff, std::little_endian>, char32_t> utf16le_cvt; // little endian
      std::wstring_convert<std::codecvt_utf16<char32_t>, char32_t> utf16be_cvt; // default big endian
      std::u32string u32_str_from_le = utf16le_cvt.from_bytes(u16le_byte_str); // utf-16 to ucs4
      std::u32string u32_str_from_be = utf16be_cvt.from_bytes(u16be_byte_str); // utf-16 to ucs4
      std::cout << "u16le_byte_str: ";
      print_code_unit_sequence(u16le_byte_str);
      std::cout << std::endl;
      std::cout << "u16be_byte_str: ";
      print_code_unit_sequence(u16be_byte_str);
      std::cout << std::endl;
      std::cout << "u32_str_from_le: ";
      print_code_unit_sequence(u32_str_from_le);
      std::cout << std::endl;
      std::cout << "u32_str_from_be: ";
      print_code_unit_sequence(u32_str_from_be);
      std::cout << std::endl;

      輸出如下

      1
      2
      3
      4
      u16le_byte_str: 0x34 0x78 0x53 0x66
      u16be_byte_str: 0x78 0x34 0x66 0x53
      u32_str_from_le: 0x00007834 0x00006653
      u32_str_from_be: 0x00007834 0x00006653

      通過(guò)設(shè)置Mode成功將不同字節(jié)序UTF-16編碼的字符串進(jìn)行了正確的轉(zhuǎn)換。

      BOM(Byte Order Mark)

      字節(jié)序標(biāo)記是插入到以UTF-8、UTF-16或UTF-32編碼Unicode文件開(kāi)頭的特殊標(biāo)記,用于標(biāo)識(shí)文本編碼及字節(jié)序。

      編碼 BOM
      UTF-8 0xEF 0xBB 0xBF
      UTF-16 BE 0xFE 0xFF
      UTF-16 LE 0xFF 0xFE
      UTF-32 BE 0x00 0x00 0xFE 0xFF
      UTF-32 LE 0xFF 0xFE 0x00 0x00

      下面的代碼演示了通過(guò)BOM指示UTF-16編碼字符串的字節(jié)序,codecvt的第3個(gè)參數(shù)需設(shè)置為std::consume_header

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      17
      18
      std::string u16le_byte_str = "\xff\xfe\x34\x78\x53\x66"; // utf-16 little endian with BOM
      std::string u16be_byte_str = "\xfe\xff\x78\x34\x66\x53"; // utf-16 big endian with BOM
      std::wstring_convert<std::codecvt_utf16<char32_t, 0x10ffff, std::consume_header>, char32_t> utf16le_cvt; // little endian
      std::wstring_convert<std::codecvt_utf16<char32_t, 0x10ffff, std::consume_header>, char32_t> utf16be_cvt; // default big endian
      std::u32string u32_str_from_le = utf16le_cvt.from_bytes(u16le_byte_str); // utf-16 to ucs4
      std::u32string u32_str_from_be = utf16be_cvt.from_bytes(u16be_byte_str); // utf-16 to ucs4
      std::cout << "u16le_byte_str: ";
      print_code_unit_sequence(u16le_byte_str);
      std::cout << std::endl;
      std::cout << "u16be_byte_str: ";
      print_code_unit_sequence(u16be_byte_str);
      std::cout << std::endl;
      std::cout << "u32_str_from_le: ";
      print_code_unit_sequence(u32_str_from_le);
      std::cout << std::endl;
      std::cout << "u32_str_from_be: ";
      print_code_unit_sequence(u32_str_from_be);
      std::cout << std::endl;

      輸出

      1
      2
      3
      4
      u16le_byte_str: 0xFF 0xFE 0x34 0x78 0x53 0x66
      u16be_byte_str: 0xFE 0xFF 0x78 0x34 0x66 0x53
      u32_str_from_le: 0x00003478 0x00005366
      u32_str_from_be: 0x00007834 0x00006653

      當(dāng)UCS4轉(zhuǎn)UTF-16時(shí)輸出為byte string,可以通過(guò)設(shè)置Mode為std::generate_header來(lái)使輸出帶BOM,下面的代碼通過(guò)UCS4轉(zhuǎn)UTF-16 LE和UTF-16 BE演示了std::generate_header的使用

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      std::u32string u32_str = U"破曉"; // ucs4
      std::wstring_convert<std::codecvt_utf16<char32_t, 0x10ffff, static_cast<std::codecvt_mode>(std::generate_header | std::little_endian)>, char32_t> utf16le_cvt; // little endian
      std::wstring_convert<std::codecvt_utf16<char32_t, 0x10ffff, static_cast<std::codecvt_mode>(std::generate_header)>, char32_t> utf16be_cvt; // default big endian
      std::string u16le_byte_str = utf16le_cvt.to_bytes(u32_str); // ucs4 to utf-16 little endian with BOM
      std::string u16be_byte_str = utf16be_cvt.to_bytes(u32_str); // ucs4 to utf-16 big endian with BOM
      std::cout << "u32_str: ";
      print_code_unit_sequence(u32_str);
      std::cout << std::endl;
      std::cout << "u16le_byte_str: ";
      print_code_unit_sequence(u16le_byte_str);
      std::cout << std::endl;
      std::cout << "u16be_byte_str: ";
      print_code_unit_sequence(u16be_byte_str);
      std::cout << std::endl;

      輸出

      1
      2
      3
      u32_str: 0x00007834 0x00006653
      u16le_byte_str: 0xFF 0xFE 0x34 0x78 0x53 0x66
      u16be_byte_str: 0xFE 0xFF 0x78 0x34 0x66 0x53

        本站是提供個(gè)人知識(shí)管理的網(wǎng)絡(luò)存儲(chǔ)空間,所有內(nèi)容均由用戶發(fā)布,不代表本站觀點(diǎn)。請(qǐng)注意甄別內(nèi)容中的聯(lián)系方式、誘導(dǎo)購(gòu)買等信息,謹(jǐn)防詐騙。如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請(qǐng)點(diǎn)擊一鍵舉報(bào)。
        轉(zhuǎn)藏 分享 獻(xiàn)花(0

        0條評(píng)論

        發(fā)表

        請(qǐng)遵守用戶 評(píng)論公約

        類似文章 更多