python的编码问题,一个小例子让人很困惑
# -*- coding:utf-8 -*-
'''
Created on 2015年10月8日
'''
def main():
s = u"你好"
d = {'id':001, 'text':s}
s1 = "你好"
d1 = {'id':002, 'text':s1}
print d
print s
print "------------"
print d1
print s1
if __name__ == "__main__": main()
输出为:
{'text': u'\u4f60\u597d', 'id': 1}
你好
------------
{'text': '\xe4\xbd\xa0\xe5\xa5\xbd', 'id': 2}
你好
为何直接打印的都是正常的汉字,但是,字典中的却是\uxxxx 或者 \x.. 之类的呢?
请高手解惑.
PS : 在使用 sqlite3 存储中文时, 及使用scrapy抓取中文数据时, 都遇到上面 字典中的情况. 很头疼.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
Ok,为了清楚解释这个问题,我假设你知道什么是编码,如果不是很清楚,可以移步这里:人机交互之字符编码。下面解释你的这段代码。
告诉Python解释器你的这个脚本编码方式为"UTF-8",然后Python解释器直接用“UTF-8”来解码这个脚本文件(当然你得确保文件编码格式确实为UTF-8)。
String vs Unicode String
s1是一个"str"类型,而s2是一个“unicode”类型,如下:
这两个类型都是Python的 Sequence Types。
str类型的字符串,内部保存的是
a plain sequence of bytes
,即任意字符串经过编码后的样子:这里我的控制台默认是UTF-8编码,所以str_1传入Python解释器的是
你好
用UTF-8编码后的字节串e4bda0e5a5bd
。在你的脚本中,你好
也会被用UTF-8编码后传递给str_1。Unicode 类型的字符串,内部保存的是
a sequence of code points
,每个码值(code points)均在0 to 0x10ffff之间,在Unicode字符集唯一对应了一个字符。也就是说对于Unicode字符串,解释器看到的是Unicode串中所有字符对应的码值序列。这里
你
在Unicode字符集对应4f60
,好
对应597d
。深入了解 print
在了解Python的print机制前,首先要了解对象的两个内建函数
__repr__
和__str__
当我们在Python中
print object
时,实际上会按照下图去执行:对于str类型和unicode类型,内置了
__str__
函数,返回便于我们阅读的字符串;而对于dict或者list类型,没有__str__
函数,因此会调用用来精确描述对象的__repr__
。dict.__str__
返回的是'object'的__str__
,说明dict没有内置__str__
。而dict内置了__repr__
,因此print dic
相当于repr(dict)
。使用scrapy抓取中文数据时:对于你获取到的数据,首先要知道它的编码格式,然后对其进行相应的编码即可。
在使用 sqlite3 存储中文时:对于你需要保存的数据,只需要将其按照sqlite3数据库的编码要求进行相应的解码即可。
更多内容
关于repr(),文档解释如下:
u"\uxxxx"
和"\x"
表示什么? 不感兴趣可以略过。下面是一些例子
相关阅读
Python str vs unicode types
Meaning of 0x and \x in python hex strings?
what does leading '\x' mean in a python string '\xaa'
Purpose of
__str__
and__repr__
in PythonPython
__str__
function printingDifference between
__str__
and__repr__
in Python返回给你的是原始编码而已,你大可以淡定。
python中,print一个非str类型的对象会隐式调用对象的__str__这个方法(实际上就是做转换成字符串的操作)
而dict(也包括list,tuple等很多python内建对象)的__str__方法中,会对字符串做这种编码处理(从而使输出都是ascii编码的字符)
如果你
print d['text']
或者print d1['text']
就可以看到你期望的结果了给你个例子
以上程序的的结果是
hello
编辑补充:
特意去查了Python的C代码,就dict这个场景而言,确实是repr而不是str,所以我上面的答案是错误的
详见: https://github.com/python/cpython/blob/2.7/Objects/dictobject.c#L1023