天天看点

《Python Cookbook(第2版)中文版》——1.20 使用Unicode来处理国际化文本

本节书摘来自异步社区《python cookbook(第2版)中文版》一书中的第1章,第1.20节,作者[美]alex martelli , anna martelli ravenscrof , david ascher ,高铁军 译,更多章节内容可以访问云栖社区“异步社区”公众号查看。

任务

需要处理包含了非ascii字符的文本字符串。

解决方案

可以在一些使用普通的字节串str类型的场合,使用python提供的内置的unicode类型。用法很简单,只要接受了在字节串和unicode字符串之间的显式转换的方式:

这里german_ae是一个unicode字符串,代表了小写的德语元音变音(umlaut,或其他分音符)字符“æ”。根据指定的utf-8编码方式,通过解析单字节字符串'xc3xa4',这段代码创建了一个unicode字符串。还有很多其他的编码方式,不过utf-8最常用,因为它是最通用的(utf-8可以编码任何unicode字符串),而且也和7位的ascii字符集兼容(任何ascii单字节字符串,也是正确的utf-8编码字符串)。

一旦跨过这一屏障,生活就变得更美好了!可以像处理普通的str字符串那样操纵unicode字符串:

注意,para是一个unicode字符串,这是因为一个unicode字符串和一个字节串之间的操作总会产生一个unicode字符串—除非这个操作发生错误并抛出异常:

字符’0xc3’不是7位ascii编码中的有效字符,python也拒绝猜测其编码。所以,在python中使用unicode的关键点是,你要随时明确编码是什么。

讨论

如果你遵守一些规范,并且学会处理一些常见的问题,则python中的unicode处理是非常简单的事情。这不是说完成一个高效的unicode实现是个简单的任务。不过,正如其他的一些难题一样,无须担心太多:只管使用python的高效的unicode实现就行了。

最重要的一点是,首先要完全接受字节串和unicode字符串的差异。正如解决方案小节所示,你经常需要通过一个字节串和一个编码方式显式地创建一个unicode字符串。不指定编码方式,字节串基本没有什么意义,除非你很有运气而且碰巧那个字节串是ascii文本。

在python中使用unicode字符串的最常见的问题是,你正在处理的文本一部分是unicode对象,另一部分则是字节串。python会简单地尝试把你的字节串隐式地转换成unicode。它通常假设那些是ascii编码,如果其中碰巧含有了非ascii字符,它会给你一个unicodedecodeerror的异常。unicodedecodeerror异常通知你,你把unicode和字节串混在了一起,而且python无法(它根本也不会去尝试)猜测你的字节串代表何种文本。

各个python大项目的开发人员们总结出了一些简单的规则,来避免这种运行时的unicodedecodeerror异常,该规则可以被总结为一句话:总是在io动作的关口做转换。下面更深入地解释一下。

无论何时,当你的程序接收到了来自“外部”的文本数据(来自网络、文件、或者用户输入等)时,应当立刻创建一个unicode对象,找出最适合的编码,如查看http头,或者寻找一个合适的转化方法来确定所用的编码方式。

无论何时,当你的程序需要向“外部”发送文本数据(发到网络、写入文件、或者输出给用户等)时,应当探察正确的编码,并用那种编码将你的文本转化成字节串。(否则,python会尝试把unicode转成ascii字节串,这很有可能发生unicodeencodeerror异常,正好是前面例子中给出unicodedecodeerror的相反情况)。

遵循这两个规则,可以解决绝大多数的unicode问题。如果你仍然遇到了那两种unicodeerror之一,应当赶快检查是否忘记了在什么地方创建一个unicode对象,或者忘记了把它转化为编码过的字节串,再或者使用了完全不正确的编码方式。(编码错误也有可能来自于用户,或者其他与你的程序进行交互的程序,因为它们没有遵循编码规则或惯例。)

为了将一个unicode字符串转回到编码过的字节串,你通常可以这么做:

现在,bytestring是德语中的用’latin1’进行编码的æ字符。注意,’xe4’(latin1)以及前面展示的’xc3xa4’(utf-8)代表了同样的德语字符,但使用了不同的编码。

至此为止,应该能够了解为什么python拒绝在几百种可能的编码中进行猜测了吧。这是一种很重要的设计选择,基于了zen of python原则中的一条:“在模糊含混面前拒绝猜测。”在任何一个python的交互式shell提示符下,输入import this语句,你就可以阅读zen of python中的重要原则。