博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Python里的string 和 unicode 区别讲得很明白的文章
阅读量:5919 次
发布时间:2019-06-19

本文共 3363 字,大约阅读时间需要 11 分钟。

hot3.png

先要弄清楚的是,在python里,string object和unicode object是两种不同的类型。

 原文博主--

string object是由characters组成的sequence,而unicode object是Unicode code units组成的sequence。
string里的character是有多种编码方式的,比如单字节的ASCII,双字节的GB2312等等,再比如UTF-8。很明显要想解读string,必需知道string里的character是用哪种编码方式,然后才能进行。
Unicode code unit又是什么东西呢?一个Unicode code unit是一个16-bit或者32-bit的数值,每个数值代表一个unicode符号。在python里,16-bit的unicode,对应的是ucs2编码。32-bit对应的是ucs4编码。是不是感觉string里character的编码没什么区别?反正我现在脑子里就是这样一个印象:在Python里,ucs2或者ucs4编码的,我们叫做unicode object,其他编码的我们就叫做string。
至于python里的unicode到底是ucs2还是ucs4的,可以在编译时指定。例如Linux下,要用ucs2做unicode的编码,可以这样
# ./configure --enable-unicode=ucs2 
# make
# make install
下载的Windows预编译版本,一般都是ucs2的。要想知道某个python运行环境是ucs2还是ucs4,可以查看sys.maxunicde,65535就是ucs2的,另一个很大的数值就是ucs4。
下面我们看看string和unicode在python里的不同
我们先看看在简体中文Windows 2003系统下,系统编码是GBK
>>> a = '你好'
>>> a
'/xc4/xe3/xba/xc3'
>>> b = u'你好'
>>> b
u'/u4f60/u597d'
>>> print a
你好
>>> print b
你好
>>> a.__class__
<type 'str'>
>>> b.__class__
<type 'unicode'>
>>> len(a)
4
>>> len(b)
2
在一个系统编码为UTF-8的Linux环境下
>>> a = '你好'
>>> a
'/xe4/xbd/xa0/xe5/xa5/xbd'
>>> b = u'你好'
>>> b
u'/u4f60/u597d'
>>> print a
你好
>>> print b
你好
>>> a.__class__
<type 'str'>
>>> b.__class__
<type 'unicode'>
>>> len(a)
6
>>> len(b)
2
如何?简单总结一下:
1、string直接用引号来表示,unicode在引号前加一个u
2、直接输入的string常量会用系统缺省编码方式来编码,例如在GBK环境下,'你好'会编码成'/xc4/xe3/xba/xc3',而在UTF-8环境下就成了'/xe4/xbd/xa0/xe5/xa5/xbd'。
3、len(string)返回string的字节数,len(unicode)返回的是字符数
4、很重要的一点,print unicode不会乱码。现在我们常用的Linux、Windows系统,都是支持unicode的,版本太老的不算。比如Windows 2003支持ucs2,所以在中文Windows2003下,除了可以正常显示缺省的GBK编码外,还可以正常显示ucs2编码。举个例子,还是在中文Windows 2003的GBK环境下:
>>>a = '/xe4/xbd/xa0/xe5/xa5/xbd' # UTF-8的'你好'
>>> print a
浣犲ソ
>>> b = unicode(a, "UTF-8")
>>> b
u'/u4f60/u597d'
>>> print b
你好
应该明白了吧?
下面再说说string和unicode的相互转换,什么unicode()、decode()、encode()、codecs之类的。

继续。

先说一下,前面提到,print(string)的时候,如果string是按当前环境编码方式编码的,可以正常输出,不会乱码;如果string不是当前编码的,就会乱码。而print(unicode)是不会乱码的。why?应为print(unicode)的时候,会把unicode先转成当前编码,然后再输出。我没看过print的源码,不过估计是这样的。
string转unicode或者unicode转string,是很常见的操作。
string和unicode都有decode()和encode()方法。decode是string2unicode,encode自然就是unicode2string。看个例子(中文Windows2003下):
>>> a = '你好'
>>> a
'/xc4/xe3/xba/xc3'
>>> b = u'你好'
>>> c = a.decode('gbk') #gbk string to unicode
>>> b == c
True
>>> c
u'/u4f60/u597d'
>>> d = b.encode('gbk') #unicode to gbk string
>>> d == a
True
>>> d
'/xc4/xe3/xba/xc3'
>>> e = b.encode('utf-8') #unicode to utf-8 string
>>> e
'/xe4/xbd/xa0/xe5/xa5/xbd'
decode或者encode的时候,如果不指定编码方式,会按照缺省编码方式来处理。查看、设置缺省编码方式可以这样做:
>>> import sys
>>> sys.getdefaultencoding()
'ascii'
>>> reload(sys) 
<module 'sys' (built-in)>
>>> sys.setdefaultencoding('gbk')
上面调用sys.setdefaultencoding()的时候先reload一下sys module,原因是python启动时缺省会import site.py, 而site.py会del sys.setdefaultencoding(),所以需要reload(sys)。具体可以看看site.py的源码。
接下来说说unicode()函数。其实unicode函数就是调用string的decode()方法,把string转成unicode,例如:
>>> a = '你好'
>>> b = unicode(a)
>>> b
u'/u4f60/u597d'
>>> c = a.decode('gbk')
>>> c
u'/u4f60/u597d'
>>> print b, c, b==c
你好 你好 True
下一部分说说codec

最后说说关于codecs。所谓的codec就是编码器和解码器(encoder and decoder)的集合。除了各种字符串编码的codec,还有各种文件格式的codec,比如压缩、解压缩的,图像的,音频的,等等。我们这里说的当然是跟字符串编码相关的了。

看看代码
>>> import codecs
>>> gbk=codecs.lookup('gbk')
>>> gbk
<codecs.CodecInfo object for encoding gbk at 0xad3ea0>
>>> gbk.decode("你好")
(u'/u4f60/u597d', 4)
>>> gbk.encode(u'/u4f60/u597d')
('/xc4/xe3/xba/xc3', 2)

转载于:https://my.oschina.net/u/993130/blog/199249

你可能感兴趣的文章
ntp时间同步服务
查看>>
Liferay:使用Web文章作为用户使用条款
查看>>
SQL Server 2005:管道的另一端上无任何进程解决方法
查看>>
D-LINK 无线路由器调试图解(DIR-600M)
查看>>
Intersting C examples
查看>>
25幅非常漂亮的闪电摄影作品
查看>>
35张非常精美的爱情桌面壁纸资源(上篇)
查看>>
openstack --help>>2.txt
查看>>
select2 的加载远程数据
查看>>
UITextField手动编写
查看>>
LVS集群之十种调度算法及负载均衡(配置篇)
查看>>
python-80:获取文章的内容
查看>>
eclipse中新建web项目
查看>>
更新日志 - fir.im「高级统计」功能上线
查看>>
网站前端_JavaScript.0012-基础入门.JavaScript函数类型
查看>>
用RecyclerView实现移动应用中常见的列表菜单
查看>>
linux网络配置文件及相关命令
查看>>
iOS开发之pch文件
查看>>
PL/SQL基础1
查看>>
读书笔记—决胜移动终端:移动互联时代影响消费者决策的6大关键
查看>>