Как преобразовать текст типа "\ 320 \ 272 \ 320 \ 276 \ 320 \ 274 ..." в std :: wstring в C ++? - PullRequest
0 голосов
/ 04 июля 2018

Я работаю над кодом, который обрабатывает сообщения из Ubuntu, некоторые сообщения содержат, например:

localhost sshd 1658 - - Неверный пользователь \ 320 \ 272 \ 320 \ 276 \ 320 \ 274 \ 320 \ 274 \ 321 \ 320 \ 275 \ 320 \ 270 \ 320 \ 267 \ 320 \ 274 из 172.28. 60,28 порт 50712]

где "\ 320 \ 272 \ 320 \ 276 \ 320 \ 274 \ 320 \ 274 \ 321 \ 320 \ 275 \ 320 \ 270 \ 320 \ 267 \ 320 \ 274" - это имя пользователя, изначально на русском языке. Как преобразовать его в std :: wstring?

Ответы [ 2 ]

0 голосов
/ 04 июля 2018

Числа после обратной косой черты являются значениями последовательности байтов UTF-8 кириллических букв, каждый байт представлен в виде восьмеричного числа.

Например, вы можете использовать регулярное выражение для замены каждого \ooo на его значение, чтобы получить реальную строку UTF-8:

Посмотреть на Wandbox

#include <iostream>
#include <string>
#include <boost/regex.hpp>

int main()
{
    std::string const source = R"(Invalid user \320\272\320\276\320\274\320\274\321\320\275\320\270\320\267\320\274 from 172.28.60.28 port 50712)";
    boost::regex const re(R"(\\\d\d\d)");

    auto const replacer = [](boost::smatch const& match, auto it) {
        auto const byteVal = std::stoi(&match[0].str()[1], 0, 8);
        *it = static_cast<char>(byteVal);
        return ++it;
    };
    std::string const out = boost::regex_replace(source, re, replacer);

    std::cout << out << std::endl;
    return EXIT_SUCCESS;
}

Если вам действительно нужно, вы можете затем преобразовать это std::string в std::wstring, используя, например, Метод Томаса .

0 голосов
/ 04 июля 2018

Если у вас есть std::string, содержащий кодовые точки UTF-8, и вы хотите преобразовать его в std::wstring, вы можете сделать это следующим образом, используя фасет std::codecvt_utf8 и std::wstring_convert шаблон класса:

#include <locale>
std::wstring convert(const std::string& utf8String) {
    std::wstring_convert<std::codecvt_utf8<wchar_t>> converter{};
    return converter.from_bytes(utf8String);
}

Формат получившегося std::wstring будет либо UCS2 (на платформах Windows), либо UCS4 (большинство платформ, отличных от Windows).

Обратите внимание, что фасет std::codecvt_utf8 устарел с C ++ 17, и вместо этого пользователям рекомендуется полагаться на специализированные библиотеки юникода / обработки текста. Но этого должно быть достаточно на данный момент.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...