将std :: string编码/解码为UTF-16

时间:2012-06-18 15:37:09

标签: c++ utf-16 stdstring

我必须处理一种文件格式(包括读取和写入),其中字符串以UTF-16编码(每个字符2个字节)。由于ASCII表中的字符很少在应用程序域中使用,因此我的C ++模型类中的所有字符串都存储在std :: string(UTF-8编码)的实例中。

我正在寻找一个库(在STL和Boost中搜索没有运气)或一组C / C ++函数来处理这个std :: string< - >从文件格式加载或保存到文件格式(实际建模为字节流)时的UTF-16转换,包括代理对的生成/识别以及所有Unicode内容(我确实不是专家)......

有什么建议吗?谢谢!

编辑:忘记提到它应该是跨平台的(Win / Mac)并且不能使用C ++ 11。

3 个答案:

答案 0 :(得分:12)

C ++ 11具有此功能:

std::string s = u8"Hello, World!";

// #include <codecvt>
std::wstring_convert<std::codecvt<char16_t,char,std::mbstate_t>,char16_t> convert;

std::u16string u16 = convert.from_bytes(s);
std::string u8 = convert.to_bytes(u16);

但据我所知,到目前为止唯一的实现是libc ++。 C ++ 11也有std::codecvt_utf8_utf16<char16_t>,其他一些实现也有。{1}}。具体来说,codecvt_utf8_utf16适用于VS 2010及更高版本,并且由于Windows使用wchar_t来表示UTF-16,因此您可以将其用于convert between UTF-8 and Windows' native encoding


  

专精化codecvt<char16_t, char, mbstate_t>在UTF-16和UTF-8编码之间转换   方案,专业化codecvt<char32_t, char, mbstate_t>在UTF-32和。之间进行转换   UTF-8编码方案。

     

- [locale.codecvt] 22.4.1.4/3


哦,std :: codecvt特化有保护析构函数,而wstring_convert需要访问析构函数,所以你真的需要一个适配器:

template <class Facet>
class usable_facet : public Facet {
public:
    using Facet::Facet; // inherit constructors
    ~usable_facet() {}

    // workaround for compilers without inheriting constructors:
    // template <class ...Args> usable_facet(Args&& ...args) : Facet(std::forward<Args>(args)...) {}
};

template<typename internT, typename externT, typename stateT> 
using codecvt = usable_facet<std::codecvt<internT, externT, stateT>>;

std::wstring_convert<codecvt<char16_t,char,std::mbstate_t>> convert;

答案 1 :(得分:4)

你看过Boost.Locale了吗? This page特别描述了如何将UTF转换为UTF转换以及如何将其与IOStream集成。

答案 2 :(得分:0)

我建议看看:

Convert C++ std::string to UTF-16-LE encoded string

并检查出iconv功能。这是一个C库,对C ++ 11没有要求。

https://github.com/win-iconv/win-iconv处还有一个Win32特定的iconv库。