python整理

python: 编码问题

2017-06-01  本文已影响289人  随风化作雨

什么是编码

任何一种语言、文字、符号等等,计算都是将其以一种类似字典的形式存起来的,比如最早的计算机系统将英文文字转为数字存储(ASCII码),这种文字与数字(或其他)一一对应的关系我们称之为编码。由于ASCII码只包含了大小写英文字母、数字和一些符号,显然当计算机推广到世界之后随着语种增多,这套编码并不适用,于是中国针对中文推出了GB2312码,但是多语言时,又不行了,于是就出现了强大的Unicode(万国码)。但是由于Unicode存储性能问题,在纯英文时存储效率要远低于ACSII码,于是又出现了现在的UTF-8编码(8-bit Unicode Transformation Format),可以看做是Unicode的加强版,通过可变长度的编码来使存储最优,而且UTF-8编码包含了ASCII码,这一点非常重要。

python处理文本时的中间编码为Unicode,于是就有了decode和encode,前者将unicode以外的字符串解码为unicode,后者将unicode编码为指定编码。

当你输入字符串时

首先,当你在python代码中输入一个字符串时候,它是以什么编码形式被保存的呢?

#!/usr/bin/python
# -*- coding: <encoding name> -*-

此时处填上编码方式,不区分大小写,其实只写下面一行就行了,上面一行只是为了在linux系统里识别而已。很多人对这种在注释中进行申明的方式很不习惯,也不解-*-是什么鬼,但是PEP 263告诉我们,这样只是为了好看而已...

注意:

设置默认编码

import sys
reload(sys)
sys.setdefaultencoding( "utf-8" )

以上代码将系统编码由ASCII码转为UTF-8编码。reload(sys)是因为import时将setdefaultencoding()方法删除了,所以将其重新载入回来。为什么说ascii是系统默认编码,因为当你使用str()给字符串encode或者是unicode()来decode时,都是默认使用了ASCII码,因此经常会报出类似"UnicodeDecodeError: 'ascii' codec can't decode byte 0xd1 in position 0"的错误,原因就是字符串里掺杂了中文,前面说到ascii码是不支持中文的。如果把系统默认编码设置为utf-8,就不会出现这样的问题了哦~

那么,它与脚本开头的"# -- coding:utf-8 --"有什么区别呢,注意,脚本开头的编码申明只是针对在脚本中输入的非英文、数字、符号的字符串如中文,将其存成utf-8的形式,而非系统转码的形式。

当开头设置默认编码时,很容易出现程序运行到setdefaultencoding就默认终止的情况(IDLE下),这时候需要在reload前后加入这个,目的是为了重新定向,防止reload将变量重置:

stdout = sys.stdout
reload(sys)
sys.stdout = stdout

IO时的编码问题

网页抓取时的编码问题

网页抓取时遇到的主要问题,无非是网页源代码中掺杂了为被转义的编码形式,被作为纯文本读了进来,比如这样一个字符串"\u6768\u777f",无论怎么print 它都是这个形式因为它是文本,不是编码,那么怎么转为中文呢,则需要用如下命令:

print text.decode('unicode_escape')

非常生动形象的,这句话相当于是把“逃离”掉的unicode编码进行再编码,于是就得到了我们想要的中文。

同样,有的网页中的文字是以反斜杠加三个数字形式呈现的,这个是标准的八进制字符串,如"\345\244\247",则表示一个中文字;而utf-8的表现形式为16进制字符串,像"\xe6\x9d\xa8"就代表着一个字 ,对于这些字符,只需要使用如下命令即可从文本转为编码字符串:

print text.decode('string_escape')
上一篇 下一篇

猜你喜欢

热点阅读