最近我遇到了一个关于字符编码的问题,而我正在深入研究字符集和字符编码这一疑点让我想到了。由于UTF-8编码与ASCII的向后兼容性,因此最受欢迎。是可变长度编码格式,它如何区分单字节和双字节字符。例如,“Aݔ”存储为“410754”(A的Unicode为41,阿拉伯字符的Unicode为0754.How编码标识41是一个字符, 0754是另一个双字节字符?为什么它不被视为4107为一个双字节字符而54为单字节字符?
答案 0 :(得分:22)
例如,“Aݔ”存储为“410754”
这不是UTF-8的工作方式。
字符U + 0000到U + 007F(也称为ASCII)存储为单个字节。它们是唯一的字符,其代码点在数字上与其UTF-8表示相匹配。例如,U + 0041变为0x41
,其为二进制0100001
。
所有其他字符都用多个字节表示。 U + 0080到U + 07FF各使用两个字节,U + 0800到U + FFFF各使用三个字节,而U + 10000到U + 10FFFF各使用四个字节。
计算机知道一个字符的结束位置和下一个字符的开始,因为UTF-8的设计使得用于ASCII的单字节值与多字节序列中使用的单字节值不重叠。字节0x00
到0x7F
仅用于ASCII而不用于其他内容; 0x7F
之上的字节仅用于多字节序列而不用于其他任何内容。此外,在多字节序列开头使用的字节也不能出现在那些序列的任何其他位置。
因此需要对代码点进行编码。考虑以下二进制模式:
110xxxxx 10xxxxxx
1110xxxx 10xxxxxx 10xxxxxx
11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
第一个字节中的1个数量告诉您有多少后续字节仍然属于同一个字符。属于该序列的所有字节均以二进制的10
开头。要对字符进行编码,请将其代码点转换为二进制并填写x。
例如:U + 0754介于U + 0080和U + 07FF之间,因此它需要两个字节。二进制文件中的0x0754
为11101010100
,因此您将x替换为这些数字:
110 11101 10 010100
答案 1 :(得分:13)
简答:
UTF-8旨在能够明确识别文本流中每个字节的类型:
您的示例Aݔ
由Unicode代码点U + 0041和U + 0754组成,以UTF-8编码为:
0 1000001 110 11101 10 010100
因此,当解码时,UTF-8知道第一个字节必须是1字节代码,第二个字节必须是2字节代码的前导字节,第三个字节必须是连续字节,并且因为第二个字节是 2字节代码的前导字节,第二个和第三个字节必须组成这个2字节代码。
请参阅here UTF-8如何编码Unicode代码点。
答案 2 :(得分:1)
请澄清一下,ASCII是指标准的7位ASCII,而不是欧洲常用的扩展的8位ASCII。
因此,第一个字节(0x80至0xFFFF)的一部分变为双字节表示,而两个字节(0x0800至0xFFFF)的第二个字节的一部分变为完整的三字节表示。
四字节表示仅使用最低的三个字节,并且仅使用16.777.215可用可能性中的1.114.111
您有一个xls here
这意味着解释器在找到那些二进制模式时必须“跳回”一个NUL(0)字节。
希望这对某人有帮助!