我在.resx
文件中有一些字符串,包括一些像这样的序列:
\u26A0 warning
所以我使用以下代码来取消它
str = Regex.Unescape(str);
现在,当我看到结果一切正常时(使用 \u
)并显示相关的表情符号。
但 Regex.Unescape(...)
方法在输入字符串包含 \U
时不起作用:
\U0001F4D8 book
并返回此错误:
错误:无法识别的转义序列 \ U
我的问题:
编辑:
当我从resx文件中读取字符串时,它有双反斜杠,我应该将这些Unicode序列转换为它们的字符:
答案 0 :(得分:3)
确实,根据Regex.Unescape
的源代码,RegexParser.ScanCharEscape
,\U
未得到处理。
相反,您可以考虑在char.ConnvertFromUtf32
的帮助下进行手动转换:
string converted = char.ConvertFromUtf32(int.Parse("0001F4D8", NumberStyles.HexNumber));
这是一份草案实施。 (令人讨厌的复杂性来自于尝试区分\U
和\\U
。)
static string Unescape(string str)
{
StringBuilder builder = new StringBuilder();
int startIndex = 0;
while(true)
{
int index = IndexOfBackslashU(str, startIndex);
if (index == -1)
return builder.Append(Regex.Unescape(str.Substring(startIndex))).ToString();
builder.Append(Regex.Unescape(str.Substring(startIndex, index - startIndex)));
string number = str.Substring(index + 2, 8);
builder.Append(char.ConvertFromUtf32(int.Parse(number, NumberStyles.HexNumber)));
startIndex = index + 10;
}
}
static int IndexOfBackslashU(string str, int startIndex)
{
while (true)
{
int index = str.IndexOf(@"\U", startIndex);
if (index == -1)
return index;
bool evenNumberOfPreviousBackslashes = true;
for (int k = index-1; k >= 0 && str[k] == '\\'; k--)
evenNumberOfPreviousBackslashes = !evenNumberOfPreviousBackslashes;
if (evenNumberOfPreviousBackslashes)
return index;
startIndex = index + 2;
}
}
答案 1 :(得分:1)
我写了这个方法,问题解决了:
public static string UnescapeIt(string str)
{
var regex = new Regex(@"(?<!\\)(?:\\u[0-9a-fA-F]{4}|\\U[0-9a-fA-F]{8})", RegexOptions.Compiled);
return regex.Replace(str,
m =>
{
if (m.Value.IndexOf("\\U", StringComparison.Ordinal) > -1)
return char.ConvertFromUtf32(int.Parse(m.Value.Replace("\\U", ""), NumberStyles.HexNumber));
return Regex.Unescape(m.Value);
});
}
unescape \u
序列和将 \U
序列转换为相关字符。所以我们可以看到表情符号。
使用:强>
str= UnescapeIt(str);
<强>更新强> 我从
改变了正则表达式\\u[0-9a-fA-F]{4}|\\U[0-9a-fA-F]{8}
到
(?<!\\)(?:\\u[0-9a-fA-F]{4}|\\U[0-9a-fA-F]{8})
如果我们在\u
或\U