操作环境:Linux mint 13 64bit,utf-8编码;python 2.7。
python的编码机制
首先应区分unicode对象和str对象:
如下:
>>> s=u"你好"
>>> a="你好"
>>> s
u'\u4f60\u597d'
>>> a
'\xe4\xbd\xa0\xe5\xa5\xbd'
>>> type(s)
<type 'unicode'>
>>> type(a)
<type 'str'>
str对象就是一个字符数组,本身可以存储任意编码的字符,例如上面的a便是存储“你好”的utf-8编码。s是unicode对象,存储的是unicode编码,unicode对象本身不会存储其他编码。
>>> s.encode("gbk")
'\xc4\xe3\xba\xc3'
>>> s.encode("utf-8")
'\xe4\xbd\xa0\xe5\xa5\xbd'
>>> type(s.encode("gbk"))
<type 'str'>
如上,s为unicode对象,encode方法可以使得unicode对象的内容转换为指定编码的str。
既然这样,str也可以转换为unicode对象,这样可以实现编码的转换,如下:
>>> a
'\xe4\xbd\xa0\xe5\xa5\xbd'
>>> print a
你好
>>> type(a)
<type 'str'>
>>> a.decode("utf-8")
u'\u4f60\u597d'
>>> type(a.decode("utf-8"))
<type 'unicode'>
>>> a.decode("utf-8").encode("gbk")
'\xc4\xe3\xba\xc3'
>>> type(a.decode("utf-8").encode("gbk"))
<type 'str'>
>>>
print 与str和unicode对象
在python中要进行str的编码转换,必须先调用str的decode方法转为unicode对象,之后调用unicode对象的encode方法获取最终结果。例如:
>>> a="你好"
>>> a.decode("utf-8").encode("gbk")
'\xc4\xe3\xba\xc3'
>>> print a.decode("utf-8").encode("gbk")
���
由于系统编码是utf-8,所以a是utf-8编码,`a.decode("utf-8").encode("gbk")`将a转为对应的gbk编码,但是print该结果时候却是乱码,这是因为print将gbk编码`\xc4\xe3\xba\xc3`给操作系统,操作系统却以utf-8形式输出其对应结果,自然就乱码。在utf-8环境中,使用print输出unicode对象会直接将其转为本地编码utf-8输出,不会乱码;而对于utf-8编码的str,print后也不会乱码。如果utf-8的str和unicode在元组或者其他高级结构中,print这些高级结构时,会输出对应的16进制编码,如下:
>>> c=("a",u"你好","你好")
>>> print c
('a', u'\u4f60\u597d', '\xe4\xbd\xa0\xe5\xa5\xbd')
>>> print c[1],c[2]
你好 你好
源文件与str
如果python源文件是utf-8编码,则源文件里的str对象均以utf-8编码存储数据。编码转换
python内部使用unicode编码,所以编码的步骤是:`初始编码-->unicode-->目的编码`。
unicode对象、str对象与索引
如下:
>>> a="你好"
>>> b=u"你好"
>>> len(a)
6
>>> len(b)
2
>>> a[0]
'\xe4'
>>> b[0]
u'\u4f60'
>>> print a[0]
>>> print b[0]
你
>>>
codecs库
这是一个处理编码的库,下面简单的展示了该如何使用:
>>> import codecs
>>> a="你好"
>>> lookup_utf_8=codecs.lookup("utf-8")
>>> lookup_gbk=codecs.lookup("gbk")
>>> lookup_utf_8.decode(a)
(u'\u4f60\u597d', 6)
>>> lookup_utf_8.decode(a)[0]
u'\u4f60\u597d'
>>> lookup_utf_8.decode(a)[0][0]
u'\u4f60'
>>> print lookup_utf_8.decode(a)[0][0]
你
>>> lookup_gbk(lookup_utf_8.decode(a)[0])
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: 'CodecInfo' object is not callable
>>> lookup_gbk.encode(lookup_utf_8.decode(a)[0])
('\xc4\xe3\xba\xc3', 2)
>>> print lookup_gbk.encode(lookup_utf_8.decode(a)[0])[0]
���
>>>
python文件读写
参考下面两个官方文档:
[7.2.1. Methods of File Objects](http://docs.python.org/2/tutorial/inputoutput.html#methods-of-file-objects)
[7.8. codecs — Codec registry and base classes](http://docs.python.org/2/library/codecs.html)
写于2013-05-02。