84

一点前景:我的任务需要将 UTF-8 XML 文件转换为 UTF-16(当然要使用正确的标题)。所以我搜索了将 UTF-8 转换为 UTF-16 的常用方法,发现应该使用<codecvt>.

但是现在当它被弃用时,我想知道做同样任务的新常用方法是什么?

(完全不介意使用 Boost,但除此之外,我更喜欢尽可能接近标准库。)

4

4 回答 4

31

别担心。

根据同一信息来源

该库组件应与附件 D 一起退役, 直到合适的替代品标准化为止

因此,在完成新的标准化、更安全的版本之前,您仍然可以使用它。

于 2017-04-01T05:07:55.940 回答
26

std::codecvt<locale>本身的模板不被弃用。对于 UTF-8 到 UTF-16,还是有std::codecvt<char16_t, char, std::mbstate_t>专攻的。

但是,由于std::wstring_convertstd::wbuffer_convert与标准转换构面一起被弃用,因此没有任何简单的方法可以使用构面转换字符串。

因此,正如 Bolas 已经回答的那样:自己实现它(或者您可以像往常一样使用第三方库)或继续使用已弃用的 API。

于 2017-03-22T08:44:35.477 回答
9

由于没有人真正回答这个问题并提供可用的替换代码,这里有一个,但它仅适用于 Windows:

#include <string>
#include <stdexcept>
#include <Windows.h>

std::wstring string_to_wide_string(const std::string& string)
{
    if (string.empty())
    {
        return L"";
    }

    const auto size_needed = MultiByteToWideChar(CP_UTF8, 0, &string.at(0), (int)string.size(), nullptr, 0);
    if (size_needed <= 0)
    {
        throw std::runtime_error("MultiByteToWideChar() failed: " + std::to_string(size_needed));
    }

    std::wstring result(size_needed, 0);
    MultiByteToWideChar(CP_UTF8, 0, &string.at(0), (int)string.size(), &result.at(0), size_needed);
    return result;
}

std::string wide_string_to_string(const std::wstring& wide_string)
{
    if (wide_string.empty())
    {
        return "";
    }

    const auto size_needed = WideCharToMultiByte(CP_UTF8, 0, &wide_string.at(0), (int)wide_string.size(), nullptr, 0, nullptr, nullptr);
    if (size_needed <= 0)
    {
        throw std::runtime_error("WideCharToMultiByte() failed: " + std::to_string(size_needed));
    }

    std::string result(size_needed, 0);
    WideCharToMultiByte(CP_UTF8, 0, &wide_string.at(0), (int)wide_string.size(), &result.at(0), size_needed, nullptr, nullptr);
    return result;
}
于 2021-10-01T18:07:14.853 回答
7

新方法是……你自己写。或者只是依赖已弃用的功能。希望标准委员会在有功能替代品之前不会真正删除codecvt。

但目前,一个都没有。

于 2017-03-28T14:20:07.747 回答