#ifdef _MSC_VER
#define _SILENCE_CXX17_CODECVT_HEADER_DEPRECATION_WARNING
#endif
#include <cstddef>
#include <cstdlib>
#include <iostream>
#include <string>
#include <algorithm>
#include <regex>
#include <codecvt>
#ifdef _WIN32
#if !defined(NOMINMAX)
#define NOMINMAX
#endif
#if !defined(WIN32_LEAN_AND_MEAN)
#define WIN32_LEAN_AND_MEAN
#endif
#include <Windows.h>
#endif
auto main() -> int
{
#ifdef _WIN32
SetConsoleOutputCP(CP_UTF8);
#endif
std::string json_string = "Json mit dem UE [u]00fc, dem AE [u]00e4 und der Kuh [u]1f42e ;-)";
std::regex unicode_regex("\\[u\\]([0-9abcdefABCDEF]{2,8})");
std::wstring_convert<std::codecvt_utf8<char32_t>, char32_t> convert;
std::string utf8_string;
std::size_t i = 0;
std::for_each(
std::sregex_iterator{
std::cbegin(json_string),
std::cend(json_string),
unicode_regex
},
std::sregex_iterator{},
[&](std::smatch match){
// JSON-String von letzter Position bis zum Match anhängen.
utf8_string.append(json_string.substr(i, match.position() - i));
// Submatch via strtoul in char32_t umwandeln, nach UTF-8
// konvertieren und anhängen.
utf8_string.append(
convert.to_bytes(
std::strtoul(match.str(1).c_str(), nullptr, 16)
)
);
i = match.position() + match.length();
}
);
// Rest des JSON-String anhängen.
utf8_string.append(json_string.substr(i));
std::cout << json_string << std::endl;
std::cout << utf8_string << std::endl;
}
I2lmZGVmIF9NU0NfVkVSCiAgICAjZGVmaW5lIF9TSUxFTkNFX0NYWDE3X0NPREVDVlRfSEVBREVSX0RFUFJFQ0FUSU9OX1dBUk5JTkcKI2VuZGlmCgojaW5jbHVkZSA8Y3N0ZGRlZj4KI2luY2x1ZGUgPGNzdGRsaWI+CiNpbmNsdWRlIDxpb3N0cmVhbT4KI2luY2x1ZGUgPHN0cmluZz4KI2luY2x1ZGUgPGFsZ29yaXRobT4KI2luY2x1ZGUgPHJlZ2V4PgojaW5jbHVkZSA8Y29kZWN2dD4KCiNpZmRlZiBfV0lOMzIKICAgICNpZiAhZGVmaW5lZChOT01JTk1BWCkKICAgICAgICAjZGVmaW5lIE5PTUlOTUFYCiAgICAjZW5kaWYKICAgICNpZiAhZGVmaW5lZChXSU4zMl9MRUFOX0FORF9NRUFOKQogICAgICAgICNkZWZpbmUgV0lOMzJfTEVBTl9BTkRfTUVBTgogICAgI2VuZGlmCiAgICAjaW5jbHVkZSA8V2luZG93cy5oPgojZW5kaWYKCmF1dG8gbWFpbigpIC0+IGludAp7CiAgICAjaWZkZWYgX1dJTjMyCiAgICAgICAgU2V0Q29uc29sZU91dHB1dENQKENQX1VURjgpOwogICAgI2VuZGlmCgogICAgc3RkOjpzdHJpbmcganNvbl9zdHJpbmcgID0gIkpzb24gbWl0IGRlbSBVRSBbdV0wMGZjLCBkZW0gQUUgW3VdMDBlNCB1bmQgZGVyIEt1aCBbdV0xZjQyZSA7LSkiOwoKICAgIHN0ZDo6cmVnZXggdW5pY29kZV9yZWdleCgiXFxbdVxcXShbMC05YWJjZGVmQUJDREVGXXsyLDh9KSIpOwogICAgc3RkOjp3c3RyaW5nX2NvbnZlcnQ8c3RkOjpjb2RlY3Z0X3V0Zjg8Y2hhcjMyX3Q+LCBjaGFyMzJfdD4gY29udmVydDsKCiAgICBzdGQ6OnN0cmluZyB1dGY4X3N0cmluZzsKICAgIHN0ZDo6c2l6ZV90IGkgPSAwOwoKICAgIHN0ZDo6Zm9yX2VhY2goCiAgICAgICAgc3RkOjpzcmVnZXhfaXRlcmF0b3J7CiAgICAgICAgICAgIHN0ZDo6Y2JlZ2luKGpzb25fc3RyaW5nKSwKICAgICAgICAgICAgc3RkOjpjZW5kKGpzb25fc3RyaW5nKSwKICAgICAgICAgICAgdW5pY29kZV9yZWdleAogICAgICAgIH0sCiAgICAgICAgc3RkOjpzcmVnZXhfaXRlcmF0b3J7fSwKICAgICAgICBbJl0oc3RkOjpzbWF0Y2ggbWF0Y2gpewogICAgICAgICAgICAvLyBKU09OLVN0cmluZyB2b24gbGV0enRlciBQb3NpdGlvbiBiaXMgenVtIE1hdGNoIGFuaMOkbmdlbi4KICAgICAgICAgICAgdXRmOF9zdHJpbmcuYXBwZW5kKGpzb25fc3RyaW5nLnN1YnN0cihpLCBtYXRjaC5wb3NpdGlvbigpIC0gaSkpOwogICAgICAgICAgICAvLyBTdWJtYXRjaCB2aWEgc3RydG91bCBpbiBjaGFyMzJfdCB1bXdhbmRlbG4sIG5hY2ggVVRGLTgKICAgICAgICAgICAgLy8ga29udmVydGllcmVuIHVuZCBhbmjDpG5nZW4uCiAgICAgICAgICAgIHV0Zjhfc3RyaW5nLmFwcGVuZCgKICAgICAgICAgICAgICAgIGNvbnZlcnQudG9fYnl0ZXMoCiAgICAgICAgICAgICAgICAgICAgc3RkOjpzdHJ0b3VsKG1hdGNoLnN0cigxKS5jX3N0cigpLCBudWxscHRyLCAxNikKICAgICAgICAgICAgICAgICkKICAgICAgICAgICAgKTsKICAgICAgICAgICAgaSA9IG1hdGNoLnBvc2l0aW9uKCkgKyBtYXRjaC5sZW5ndGgoKTsKICAgICAgICB9CiAgICApOwogICAgLy8gUmVzdCBkZXMgSlNPTi1TdHJpbmcgYW5ow6RuZ2VuLgogICAgdXRmOF9zdHJpbmcuYXBwZW5kKGpzb25fc3RyaW5nLnN1YnN0cihpKSk7CgogICAgc3RkOjpjb3V0IDw8IGpzb25fc3RyaW5nIDw8IHN0ZDo6ZW5kbDsKICAgIHN0ZDo6Y291dCA8PCB1dGY4X3N0cmluZyA8PCBzdGQ6OmVuZGw7Cn0=