var combined = arr.reduce(function(a, item, idx) {
var found = false;
for (var i = 0; i < a.length; i++) {
if (a[i].id == item.id) {
a[i].classes = a[i].classes.concat(item.classes);
found = true;
break;
}
}
if (!found) {
a.push(item);
}
return a;
}, []);
在Visual Studio中运行此代码,输出
char[] chars = new char[]
{
(char)0xd83d, (char)0xde04,
};
byte[] bytes = Encoding.UTF32.GetBytes(chars);
Console.WriteLine("bytes.Length = " + bytes.Length);
foreach (var b in bytes)
{
Console.WriteLine(b.ToString("x2"));
}
但在Unity中,输出是
bytes.Length = 4
04
f6
01
00
为什么?
B.T.W。 0xd83d,0xde04是一个表情符号。它应该等于Unicode U + 1F604,所以我认为bytes.Length = 8
04
f6
01
00
00
00
00
00
应该是4(一个UInt32)。
----------------编辑------------------------------ ---
在Visual Studio中,bytes.Length
返回原始字符 p>
但在Unity中,Encoding.UTF32.GetChars(the 4 bytes)
会返回不同的字符
所以我认为这是一个错误
答案 0 :(得分:1)
右键单击.ToString("x2")
,然后“转到定义”。
你会在常规的VS项目中看到:
C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5.2\mscorlib.dll
但是在Unity项目中你会得到:
C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v3.5\Profile\Unity Subset v3.5\mscorlib.dll
我怀疑框架版本(3.5 vs 4.5)是原因。我认为“统一子集”的实现方式不同。
现在,如果你问为什么统一子集的dll以它的方式实现它 - 我不知道。
答案 1 :(得分:1)
看起来编码可能会在那里偷一个空终结器。分离32位值:
0x04 0xf6 0x01 0x00 // 0x0001f604
0x00 0x00 0x00 0x00 // 0x00000000 (NUL)
如果顶行看起来令人困惑,那是因为字节顺序是小端的。
因此,Encoding.UTF32.GetBytes
首先正确输出UTF-16代理对作为UTF-32字符,并附加一个空字符。
不幸的是,由于我没有兼容的机器,我现在无法对此进行测试,但请尝试以下方法:
将代理对(char)0xd83d, (char)0xde04
两次添加到char
数组中并运行相同的程序 - 如果bytes
的长度为12且最后四个字节全为零则为答案是合理的,如果长度为16(并且字节只是两个相同的八字节序列),似乎编译器出于某种原因使用64位UInt
来表示UTF-32字符。
请考虑关注Microsoft's suggestion:
考虑使用Encoder.Convert方法而不是GetByteCount。转换方法转换尽可能多的数据,如果输出缓冲区太小,则会抛出异常。对于流的连续编码,此方法通常是最佳选择。