设为首页 加入收藏

TOP

字符、字符集、编码,以及它们python中会遇到的一些问题(下)(二)
2017-09-30 15:33:53 】 浏览:11052
Tags:字符 字符集 编码 以及 它们 python 遇到 一些 问题
3、程序会通过头部声明,解码初始化 u"人生苦短",这样的unicode对象,(所以头部声明和代码的存储格式要一致)

    (2)在没有指定代码文件的编码时,创建代码文件时使用的是python默认采用的编码(一般来说是ascii码,在windows中实际保存为cp936(GBK)编码)。通过sys.getdefaultencoding()和sys.setdefaultencoding('...')来获取和设置该默认编码。

   

终端输入输出编码:sys.stdin.encoding,sys.stdout.encoding,必须与locale编码保持一致,才能print出正确str。

print会根据sys.stdout.encoding再转一次码。 

   

  1. sys.stdout.encoding
  2. 'cp936'
  3. '严'
  4. '\xe4\xb8\xa5'
  5. print u'严'
  6. print u'严'.encode('utf-8')
  7. print u'严'.encode('gbk')
  8. u'严'.encode('utf-8')
  9. '\xe4\xb8\xa5'
  10. u'涓'.encode('gbk')
  11. '\xe4\xb8'

       

       

print打印显示的过程

Python2.7中调用print打印var 变量时,操作系统会对var做一定的字符处理:如果var是str类型的变量,则直接将var变量交付给终端进行显示;如果var变量是unicode类型,则操作系统首先将var编码成str类型的对象(编码格式取决于stdout的编码格式),然后再交由终端进行显示。在终端显示时,如果str类型的变量的编码方式和终端设置的编码方式不一致,很可能会出现乱码问题。

还有就是print字符串的时候出现的编码错误问题。原因在于sys.stdout.encoding。print 后面跟的字符串对象的编码类型一定要与sys.stdout.encoding所指定的一致,不一致就会出现编码错误。

console不能正常显示中文,console的编码是由操作系统决定的(windows环境下);

我的操作系统是win8中文版(GBK)

console的编码决定了sys.stdout.encoding的取值,sys.stdout.encoding='cp936'

   

decode && encode :

decode:解码(从其他方向(utf-8,gbk等.......)到unicode)

   

  1. #gbk就是源码的编码方式,解码成了unicode
  2. '\xa1\xb0'.decode('gbk') #解码
  3. u'\u201c' #unicode

encode:编码(从unicode到其他方向(utf-8,gbk等.......))

   

  1. u'中文'.encode('utf-8')
  2. '\xe4\xb8\xad\xe6\x96\x87'

   

 简单来说就是,你用的什么规则去编码,你就得用这个规则去解码,否则,要不然就乱码了,要不然就直接报错,没法解啊!!!

但问题就是呢,系统有系统的默认编码格式,你文件明明是utf-8的编码,他偏偏用gbk方式去解码,那要不然就直接解不了,要不然就是牛头不对马嘴呗。

   

关于打印:

你在打印str的时候,实际就是直接将字节流发送给shell。如果你的字节流编码格式与shell的编码格式不相同,就会乱码。

而你在打印unicode的时候,系统自动将其编码为shell的编码格式,是不会出现乱码的。

   

其他命令:

文件系统的编码:sys.getfilesystemencoding()

终端的输入编码:sys.stdin.encoding

终端的输出编码:sys.stdout.encoding

   

一些建议:

1. 使用字符编码声明,并且同一工程中的所有源代码文件使用相同的字符编码声明;

2. 抛弃str,全部使用unicode:按引号前先按一下u,这么做可以减少90%的编码问题;

3. 使用codecs.open()替代内置的open();

4. 绝对需要避免使用的字符编码:MBCS/DBCS和UTF-16;

5、主动设置defaultencoding。(默认的是ascii);

6、代码文件的保存格式要与文件头部的# coding:xxx一致。

   

其他:

python 3和2很大区别就是python本身改为默认用unicode编码,字符串不再区分"abc"和u"abc", 字符串"abc"默认就是unicode,不再代表本地编码。

python2.7以后不用setdefaultencoding了,这两个(声明头部和setdefaultencoding)是没有区别的

这两个作用不一样:

     1. # coding:utf-8 作用是定义源代码的编码。如果没有定义, 此源码中是不可以包含中文字符串的;

    2. sys.getdefaultencoding() 是设置默认的string的编码格式。

   

问题的根源:Python2 中的 string

Python 为了让其语法看上去简洁好用,做了很多 tricky 的事情,混淆 byte string 和 text string 就是其中一例。

在 Python 里,有三大类 string 类型,unicode(text string),str(byte string,二进制数据),basestring,是前两者的父类。

其实,在语言设计领域,一串字节(sequences of bytes)是否应该当做字符串(string)一直是存在争议的。我们熟知的 Java 和 C# 投了反对票,而 Python 则站在了支持者的阵营里。其实我们在很多情况下,给文本做的操作,比如正则匹配、字符替换等,对于字节来说是用不着的。而 Python 认为字节就是字符,所以他们俩的操作集合是一致的。

然后进一步的,Python 会在必要的情况下,尝试对字节做自动类型转换,例如,在上文中的 ==,或者字节和文本拼接时。如果没有一个编码(encoding),两个不同类型之间的转换是无法进行的,于是,Python 需要一个默认编码。在 Python2 诞生的年代,ASCII 是最流行的(可以这么说吧),于是 Python2 选择了 ASCII。然而,众所周知,在需要需要转换的场景,ASCII 都是没用的(128个字符,够什么吃)。

在历经这么多年吐槽后,Python 3 终于学乖了。默认编码是 Unicode,这也就意味着,做所有需要转换的场合,都能正确并成功的转换。

   

一个非常困惑不解的地方:

打开ipython,一开始就运行

首页 上一页 1 2 3 下一页 尾页 2/3/3
】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
上一篇使用haystack实现django全文检索.. 下一篇学习笔记GAN001:生成式对抗网络,..

最新文章

热门文章

Hot 文章

Python

C 语言

C++基础

大数据基础

linux编程基础

C/C++面试题目