python 字符编码处理问题总结 彻底击碎乱码!
Python中经常遇到这样的字符编码问题,尤其在处理网页源码时(特别是爬虫中):
UnicodeDecodeError: ‘XXX' codec can't decode bytes in position 12-15: illegal multibyte...
下面以汉字'哈'来解释作示例解释所有的问题,汉字“哈”的各种编码如下:
1 UNICODE(UTF8-16): 0xC854
2 UTF-8: 0xE59388
3 GBK: 0xB9FE
除此之外还有如gb2312, big5等。例如一些含有繁体字的页面,比如www.google.com.hk首页中用的就是big5码,
不知道港台的码农同时处理简体字繁体字是不是更郁闷 :)
一直以来,python中的中文编码就是一个大问题,为他他并不能智能识别编码,而实际上其他语言也很难做到。
在html的header里一般都可以找到字符编码例如:
<meta http-equiv="Content-Type" content="text/html;charset=gb2312"/>
当然这不是我们研究的重点,更多的时候是我们得知一个字符串是GBK编码, 而要用print等正确的打印出来却不容易...
首先,在python中提到unicode,一般指的是unicode对象,例如'哈哈'的unicode对象为u'\u54c8\u54c8'
而str是一个字节数组,这个字节数组表示的是对unicode对象编码后(如utf-8、gbk、cp936、GB2312)的存储的格式,这里它
仅是一个字节流,没有其它的含义,如果你想使这个字节流显示的内容有意义,就必须用正确的编码格式,解码显示。
例如:(注意是在windows下)
s = u'哈哈'
s_utf8 = s.encode('utf-8')
pirnt s_utf8
>>> 鍝堝搱
悲剧...
s_utf8这时实际上是'\xe5\x93\x88\xe5\x93\x88'
而下面的代码才可以正常显示:
s_gdb = s.encode('gbk') # s_gdk 这时是'\xb9\xfe\xb9\xfe'
print s_gbk
>>> 哈哈 #正常了
因为print语句它的实现是将要输出的内容传 送了操作系统,操作系统会根据系统的编码对输入的字节流进行编码,这就解释了
utf-8格式的字符串“哈哈”,输出的是“鍝堝搱”,因为 '\xe5\x93\x88\xe5\x93\x88'用GB2312去解释,其显示的出来就
“鍝堝搱”。
这里再强调一下,str记录的是字节数组,只是某种编码的存储格式,至于输出到文件或是打印出来是什么格式,
完全取决其解码的编码将它解码成什么样子。
这里再对print进行一点补充说明:当将一个unicode对象传给print时,在内部会将该unicode对象进行一次转换,
转换成本地默认编码(这仅是个人猜测)
str和unicode对象的转换,通过encode和decode实现,具体使用如下:再次强调windows下:
s = '哈哈'
print s.decode('gbk').encode('utf-8')
>>> 鍝堝搱
反之亦然,有兴趣可以尝试其他转换
有时当我们遇到把s(gbk字符串)直接编码成utf-8的时候,将抛出异常,但是通过调用如下代码:
import sys
reload(sys)
sys.setdefaultencoding('gbk')
后就可以转换成功,为什么呢?
在python中str和unicode在编码和解码过程中,如果将一个str直接编码成另一种编码,会先把str解码成unicode,
采用默认编码,一般默认编码是anscii,所以在上面示例代码中第一次转换的时候会出错,
当设定当前默认编码为'gbk'后,就不会出错了。
至于reload(sys)是因为Python2.5 初始化后会删除 sys.setdefaultencoding 这个方法,我们需要重新载入。
一般不推荐这样使用。本来reload都是应该避免使用的函数。
对于操作不同文件的编码格式的文件,也会遇到这样的问题
建立一个文件test.txt,文件格式用ANSI,内容为:
abc中文
然后用python来读取
# coding=gbk
print open("Test.txt").read()
结果:abc中文
把文件格式改成UTF-8:
结果:abc涓枃,显然,这里需要解码:
# coding=gbk
import codecs
print open("Test.txt").read().decode("utf-8")
结果:abc中文
上面的test.txt我是用Editplus来编辑的,但当我用Windows自带的记事本编辑并存成UTF-8格式时,
运行时报错:
Traceback (most recent call last):
File "ChineseTest.py", line 3, in
print open("Test.txt").read().decode("utf-8")
UnicodeEncodeError: 'gbk' codec can't encode character u'\ufeff' in position 0: illegal multibyte sequence
原来,某些软件,如notepad,在保存一个以UTF-8编码的文件时,
会在文件开始的地方插入三个不可见的字符(0xEF 0xBB 0xBF,即BOM)。
因此我们在读取时需要自己去掉这些字符,python中的codecs module定义了这个常量:
# coding=gbk
import codecs
data = open("Test.txt").read()
if data[:3] == codecs.BOM_UTF8:
data = data[3:]
print data.decode("utf-8")
结果:abc中文
最后,有些时候编码搞对了,但是遇到了非法字符,比如产生字符串的来源发生错误,引入了错误值等,这时再次遇到异常
例如:全角空格往往有多种不同的实现方式,比如\xa3\xa0,或者\xa4\x57,
这些字符,看起来都是全角空格,但它们并不是“合法”的全角空格
真正的全角空格是\xa1\xa1,因此在转码的过程中出现了异常。
而之前在处理新浪微博数据时,遇到了非法空格问题导致无法正确解析数据。
解决办法:
将获取的字符串strTxt做decode时,指明ignore,会忽略非法字符,
当然对于gbk等编码,处理同样问题的方法是类似的
strTest = strTxt.decode('utf-8', 'ignore')
return strTest
默认的参数就是strict,代表遇到非法字符时抛出异常;
如果设置为ignore,则会忽略非法字符;
如果设置为replace,则会用?号取代非法字符;
如果设置为xmlcharrefreplace,则使用XML的字符引用。
其他的以后遇到再总结.....
python 字符编码处理问题总结 彻底击碎乱码!相关推荐
- python 字符编码问题
字符编码 一.字符编码的演进 ASCII GB2312 GBK1.0 GB18030 Unicode编码:国际标准字符集,它将世界各种语言的每个字符定义一个唯一的编码,以满足跨语言.跨平台 ...
- Python字符编码详解
Python字符编码详解 转自http://www.cnblogs.com/huxi/archive/2010/12/05/1897271.html Python字符编码详解 本文简单介绍了各种常用的 ...
- python字符编码是什么_python3字符编码是什么?怎么用?
最近一直讲的是python基础方面的知识,小编一直在考虑要不要加大难度.这个问题犹豫了很久,怕一些python小白不能很好的接受知识点.但是最近小编收到不少小伙伴的强烈要求,想要学习编码这个模块的知识 ...
- 【转】python 字符编码与解码——unicode、str和中文:UnicodeDecodeError: 'ascii' codec can't decode...
原文网址:http://blog.csdn.net/trochiluses/article/details/16825269 摘要:在进行python脚本的编写时,如果我们用python来处理网页数据 ...
- 深入理解Python字符编码--转
http://blog.51cto.com/9478652/2057896 不论你是有着多年经验的 Python 老司机还是刚入门 Python 不久,你一定遇到过UnicodeEncodeError ...
- python字符编码在哪里_快速入手Python字符编码
前言 对于很多接触python的人而言,字符的处理和语言整体的温顺可靠相比显得格外桀骜不驯难以驾驭. 文章针对Python 2.7,主要因为3对的编码已经有了很大的改善并且实际原理一样,更改一下操作命 ...
- python 字符编码处理_浅析Python 字符编码与文件处理
Python字符编码 目前计算机内存的字符编码都是Unicode,目前国内的windows操作系统采用的是gbk. python2默认的字符编码方式是ASCII python3默认的字符编码方式是Un ...
- 关于python字符编码_关于python文件的字符编码
# -*- coding: utf-8 -*-字符编码是啥? 在弄清楚字符编码是啥之前我们要先考虑一个问题.如果计算机最基础的就是0和1,那么他们是如何识别我们输入的英文字母和数字的. 下面是数学知识 ...
- 转1:Python字符编码详解
Python27字符编码详解 声明 一 字符编码基础 1 抽象字符清单ACR 2 已编码字符集CCS 3 字符编码格式CEF 31 ASCII初创 311 ASCII 312 EASCII 32 MB ...
最新文章
- hadoop块的存储方式
- 面向对象三大特性之一:继承(C++)
- Fiori Elements value help的工作原理
- 设置LD_LIBRARY_PATH不起作用解决
- 可变对象 不可变对象区别_对象应该是不可变的
- [转]关于内存泄露测试工具
- 景安mysql主机_景安虚拟主机使用教程
- python处理数据快吗_python (七、Numpy高效数据处理)
- 解决C#网络通信编程的阻塞问题
- vim 配置文件 (未完待续)
- android 进入三方应用动画,Android 动画各种实现总结分享 AndroidAnimationExercise
- gre作文3.5什么水平计算机专业,gre作文3.5分如何达到
- 页面版权声明©xx公司写法
- 核桃编程C语言,核桃编程毕业设计获奖感言?
- ORB-SLAM2源码学习(一)
- 20200615 碎碎念
- 代码重构的力量:如何衡量重构成功
- 利用ms16-032提权并打开3389端口
- 2021-09-05meituan -001小美的用户名
- https://www.cnblogs.com/xinxin1994/p/5257472.html oracle 创建用户
热门文章
- redirect-重定向
- android输入法框架分析,Android与iOS输入法开发框架比较谈
- mysql查看数据库事务隔离级别_MySQL查看和修改事务隔离级别的实例讲解
- 北京个人社保查询方法
- 嵌入式linux 修改mac,MAC to MAC 环境下,嵌入式linux的修改
- python求导并作图_科学网—python-符号运算(求导等) - 夏江江的博文
- Lighthouse performance scoring
- log4的配置和使用
- 职称英语与计算机考试试题,2017职称计算机考试Word模拟题及答案
- DHCP和交换机的工作原理