1、Python & Unicode (《Dive into python》)
例 9.13. unicode 介绍
>>> s = u'Dive in'
>>> s
u'Dive in'
>>> print s
Dive in
例 9.14. 存储非 ASCII 字符
>>> s = u'La Pe\xf1a'
>>> print s
Traceback (innermost last):
File "<interactive input>", line 1, in ?
UnicodeError: ASCII encoding error: ordinal not in range(128)
>>> print s.encode('latin-1')
La Peña
还记得我说过:需要从一个 unicode 得到一个正常字符串时,Python 通常默认将 unicode 转换成 ASCII 吗?嗯,这个默认编码模式是一个可以定制的选项。
例 9.15. sitecustomize.py
# sitecustomize.py
# this file can be anywhere in your Python path,
# but it usually goes in ${pythondir}/lib/site-packages/
import sys
sys.setdefaultencoding('iso-8859-1')
例 9.16. 设置默认编码的效果
>>> import sys
>>> sys.getdefaultencoding()
'iso-8859-1'
>>> s = u'La Pe\xf1a'
>>> print s
La Peña
例 9.17. 指定.py文件的编码
如果你打算在你的 Python 代码中保存非 ASCII 字符串,你需要在每个文件的顶端加入编码声明来指定每个 .py 文件的编码。这个声明定义了 .py 文件的编码为 UTF-8:
#!/usr/bin/env python
# -*- coding: UTF-8 -*-
现在,想想 XML 中的编码应该是怎样的呢?不错,每一个 XML 文档都有指定的编码。重复一下,ISO-8859-1 是西欧语言存放数据的流行编码方式。KOI8-R 是俄语流行的编码方式。编码――如果指定了的话――都在 XML 文档的首部。
2、Python正则表达式
有了上面的基础,实践一个小应用问题的解决,用python正则表达式取匹配串(当然包含中文了)
仅英文情况下(ASCII),下面的代码是可以的,test.py(文件编码为默认)
当字符串s中有中文时,须如下方可,test1.py(文件编码也是utf-8)
# 若encode成utf-8 cmd显示亦是乱码,但输出给web页面肯定没问题,因为浏览器支持utf-8啊
当然也可以在pattern串中用\u声明具体中文(或其他文)字符,不采用上述的方式(unicode->utf-8)
相关python unicode i/o参见这篇文章http://bakey1985.blogspot.com/2009/01/python-unicode-io.html
3、Python web 开发
用python的web framework进行web开发时,同样需要考虑编码问题,统一编码(python sys、所有文件编码、code文件内的编码声明)避免n多问题
python2.x下对unicode的支持,至少需要你对其有基本的了解方容易解决问题,当然不能跟java、c#相比了,毕竟是从非unicode发展过来的。
UnicodeError: ASCII encoding error: ordinal not in range(128)
>>> print s.encode('latin-1') 3
La Peña
1 unicode 真正的优势,理所当然的是它保存非 ASCII 字符的能力,例如西班牙语的 “ñ”(n 上带有一个波浪线)。用来表示波浪线 n 的 unicode 字符编码是十六进制的 0xf1 (十进制的241),你可以像这样输入:\xf1。
2 还记得我说过 print 函数会尝试将 unicode 字符串转换为 ASCII 从而打印它吗?嗯,在这里将不会起作用,因为你的 unicode 字符串包含非 ASCII 字符,所以 Python 会引发 UnicodeError 异常。
3 这儿就是将 unicode 转换为其它编码模式起作用的地方。s 是一个 unicode 字符串,但 print 只能打印正常的字符串。为了解决这个问题,我们调用 encode 方法 (它可以用于每个 unicode 字符串) 将 unicode 字符串转换为指定编码模式的正常字符串。我们向此函数传入一个参数。在本例中,我们使用 latin-1 (也叫 iso-8859-1),它包括带波浪线的 n (然而缺省的 ASCII 编码模式不包括,因为它只包含数值从 0 到 127 的字符)。
还记得我说过:需要从一个 unicode 得到一个正常字符串时,Python 通常默认将 unicode 转换成 ASCII 吗?嗯,这个默认编码模式是一个可以定制的选项。
例 9.15. sitecustomize.py
# sitecustomize.py 1
# this file can be anywhere in your Python path,
# but it usually goes in ${pythondir}/lib/site-packages/
import sys
sys.setdefaultencoding('iso-8859-1') 2
1 sitecustomize.py 是一个特殊的脚本;Python 会在启动的时候导入它,所以在其中的任何代码都将自动运行。就像注解中提到的那样,它可以放在任何地方 (只要 import 能够找到它),但是通常它位于 Python 的lib 目录的 site-packages 目录中。
2 嗯,setdefaultencoding 函数设置默认编码。Python 会在任何需要将 unicode 字符串自动转换为正规字符串的地方,使用这个编码模式。
例 9.16. 设置默认编码的效果
>>> import sys
>>> sys.getdefaultencoding() 1
'iso-8859-1'
>>> s = u'La Pe\xf1a'
>>> print s 2
La Peña
1 这个例子假设你已经按前一个例子中的改动对 sitecustomize.py 文件做了修改,并且已经重启了 Python。如果你的默认编码还是 'ascii',可能你就没有正确设置 sitecustomize.py 文件,或者是没有重新启动 Python。默认的编码只能在 Python 启动的时候改变;之后就不能改变了。(由于一些我们现在不会仔细研究的古怪的编程技巧,你甚至不能在 Python 启动之后调用 sys.setdefaultencoding 函数。仔细研究 site.py,并搜索 “setdefaultencoding” 去发现为什么吧。)
2 现在默认的编码模式已经包含了你在字符串中使用的所有字符,Python 对字符串的自动强制转换和打印就不存在问题了。
例 9.17. 指定.py文件的编码
如果你打算在你的 Python 代码中保存非 ASCII 字符串,你需要在每个文件的顶端加入编码声明来指定每个 .py 文件的编码。这个声明定义了 .py 文件的编码为 UTF-8:
#!/usr/bin/env python
# -*- coding: UTF-8 -*-
现在,想想 XML 中的编码应该是怎样的呢?不错,每一个 XML 文档都有指定的编码。重复一下,ISO-8859-1 是西欧语言存放数据的流行编码方式。KOI8-R 是俄语流行的编码方式。编码――如果指定了的话――都在 XML 文档的首部。