Одна проблема, которую я вижу, состоит в том, что \u...
последовательности символов всегда состоят из 6 символов, но вы ищете только и заменяете 4 символа, оставляя остальные 2 символа в строке.
Кроме того, вы ищете все последовательности заранее, но при этом вы не принимаете во внимание, что любые замены, сделанные pos1
l oop, сделают недействительными pos2
, pos3
и pos4
. Тогда любые замены, сделанные pos2
l oop, сделают недействительными pos3
и pos4
. И так далее.
Я бы предложил совершенно другую стратегию разбора:
#include <string>
#include <sstream>
#include <iomanip>
...
auto pos = str2.find('\\');
char ch;
while (pos != std::string::npos)
{
if (++pos == str2.size())
break;
switch (str2[pos])
{
case 'r':
ch = '\r';
str2.replace(pos-1, 2, &ch, 1);
/* or:
str2.replace(--pos, 2, "");
*/
break;
case 'n':
ch = '\n';
str2.replace(pos-1, 2, &ch, 1);
break;
case 't':
ch = '\t';
str2.replace(pos-1, 2, &ch, 1);
break;
case '\\':
ch = '\\';
str2.replace(pos-1, 2, &ch, 1);
break;
case 'u': {
std::istringstream iss(str2.substr(pos+1, 4));
unsigned short u;
if (!(iss >> std::hex >> u)) {
ch = '?';
}
else
{
switch (u)
{
case 0x2019:
ch = '\'';
break;
...
default:
if (u <= 256)
ch = static_cast<char>(u);
else
ch = '?';
break;
}
}
str2.replace(pos-1, 6, &ch, 1);
break;
}
}
pos = str2.find('\\', pos);
}
Live Demo