网络寻租

Programmer, Gamer, Hacker

Utf8介绍

| Comments

今天学习了一下utf8的相关概念, 发现自己的理解还是不很透彻, 这里整理一下:

什么是UCS?

我们首先需要知道如何标识一个具体的字符, 国际上对于字符标识有一个东西, 叫UCS, 全称: Universal Character Set,

它是关于所有字符编码的标准. 简单地说, 为了能够规范我们所有字符的表示形式, 把所有字符都映射成一张表, 每个字符都指代单独的一个数字做标识.

什么是UTF-8?

上面的UCS只是表示字符的标识, 并没有说明具体的表示方式是什么. 所以就有了UTF-8, 用来把UCS转换成计算机能够处理的字符串. 它为了节省空间, 方便解析和除错做了优化. 具体表示方式如下:

  • 小于u80的字符, 直接打印为一个字符, 这个是为了和ASCII标准兼容.
  • 大于等于u80小于u800的字符, 分割成2个字符, 第一个字符开始为110, 第二个字符开始为10, 拆分的方法是先填满后面的字符(等会看后面的例子).
  • 以此类推…

说的不是太清楚, 这里有一个UCS映射到UTF-8的表, 一看就明白了:

U-00000000 – U-0000007F:    0xxxxxxx
U-00000080 – U-000007FF:    110xxxxx 10xxxxxx
U-00000800 – U-0000FFFF:    1110xxxx 10xxxxxx 10xxxxxx
U-00010000 – U-001FFFFF:    11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
U-00200000 – U-03FFFFFF:    111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
U-04000000 – U-7FFFFFFF:    1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx

同时, 长的表示方式不能涵盖短的表示方式, 所以下面的范围是错误的(可以快速排除错误):

1100000x (10xxxxxx)
11100000 100xxxxx (10xxxxxx)
11110000 1000xxxx (10xxxxxx 10xxxxxx)
11111000 10000xxx (10xxxxxx 10xxxxxx 10xxxxxx)
11111100 100000xx (10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx)

我们来看具体的例子(python代码):

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
# 比如©这个符号, UCS的标识为: \u00a9:
>>> print u"\u00A9"
©

# 我们把a9转换成真正的表示方式:
>>> u"\u00A9".encode('utf8')
'\xc2\xa9'

# 我们也可以把真正的表示方式转换成标准里面的标识.
>>> '\xc2\xa9'.decode('utf8')
u'\xa9'

# 我们来看一个分割的例子:
>>> print u'\u2260'


# 转换成utf8就被拆散了:
# u+2260 = 0010 0010 0110 0000
# 11100010 10001001 10100000 = 0xE2 0x89 0xA0
>>> u'\u2260'.encode('utf8')
'\xe2\x89\xa0'

结论

现在还没有什么心得, 总之, 了解了上面的概念, 才能处理好平时遇到的字符编码问题.

参考资料: – http://www.cl.cam.ac.uk/\~mgk25/unicode.html

Comments