Python编解码问题及文本文件处理方法详解


Posted in Python onJune 20, 2021

编解码器

在字符与字节之间的转换过程称为编解码,Python自带了超过100种编解码器,比如:

  • ascii(英文体系)
  • UTF-8(中文体系)
  • utf-8(全球通用)
  • latin1
  • utf-16

编解码器一般有多个别名,比如utf8、utf-8、U8。

这些编解码器可以传给open()、str.encode()、bytes.decode()等函数的encoding参数。

UnicodeEncodeError

多数非UTF编解码器(比如cp437)只能处理Unicode字符的一小部分子集。把字符转换成字节时,如果目标编码中没有定义这个字符,那么就会抛出UnicodeEncodeError异常。

处理方式一:使用utf8编码。

处理方式二:添加errors参数:

# 忽略 如b'So Paulo'
city.encode("cp437", errors="ignore")
# 替换为? 如b'S?o Paulo'
city.encode("cp437", errors="replace")
# 替换为XML实体 如b'São Paulo'
city.encode("cp437", errors="xmlcharrefreplace")

UnicodeDecodeError

把字节转换为字符时,遇到无法转换的字节时会抛出UnicodeDecodeError异常。这是因为不是每个字节都包含有效的ASCII字符,也不是每个字符都是有效的UTF-8。

处理方式也有两种,跟上面一样。

SyntaxError

Python3默认使用UTF-8编码源码。如果加载的.py模块中包含UTF-8之外的数据,而且没有声明编码,就会抛出SyntaxError异常。

处理方式是在文件顶部添加coding注释:

# coding: cp1252

但是这个办法并不好,最好还是找到这些报错字符,把它们转换为UTF-8。

从网上直接复制代码到IDE中执行经常会报这个错。

处理文本文件

Unicode三明治:

Python编解码问题及文本文件处理方法详解

在程序中尽量少接触二进制,把字节解码为字符,只处理字符串对象。比如在Django中,view应该输出Unicode字符串,Django会负责把响应数据编码成字节序列,而且默认使用UTF-8编码。

Python内置的open函数就是采用了这个原则,在读取文件时会做必要的解码,以文本模式写入文件时会做必要的编码。

文件乱码

Windows更容易遇到这个问题,因为Windows并不是统一的UTF-8编码,比如在Windows10中:

>>> open("cafe.txt", "w", encoding="utf8").write("café")
4
>>> open("cafe.txt").read()
'caf茅'

写入文件时指定了utf8,但是读取文件没有指定,Python就会使用系统默认编码:

>>> import locale
# 打开文件用这个
# 如果没有设置PYTHONENCODING环境变量,sys.stdout/stdin/stderr也用这个
>>> locale.getpreferredencoding()
'cp936'

cp936把最后一个字节解码成了茅而不是é。

>>> import sys
# 二进制数据和字符串之间转换用这个
>>> sys.getdefaultencoding()
'utf-8'
>>> import sys
# 文件名(不是文件内容)用这个
>>> sys.getfilesystemencoding()
'utf-8'

GNU/Linux或Mac OS X不会遇到这个问题,因为多年来它们的默认编码都是UTF-8。

解决办法是一定不能依赖系统默认编码,打开文件时始终应该明确传入encoding=参数,因为不同的设备使用的默认编码可能不同,有时隔一天也会发生变化。

小结

本文介绍了Python的编解码器,以及可能出现的UnicodeEncodeError、UnicodeDecodeError、SyntaxError问题,然后给出了Python的open函数处理文本文件的原则,最后对Windows容易出现的文件乱码问题进行了说明。

到此这篇关于Python编解码问题及文本文件处理方法的文章就介绍到这了,更多相关Python编解码及文本处理内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Python 相关文章推荐
详解Python中的__init__和__new__
Mar 12 Python
python下paramiko模块实现ssh连接登录Linux服务器
Jun 03 Python
Python之os操作方法(详解)
Jun 15 Python
Python中defaultdict与lambda表达式用法实例小结
Apr 09 Python
pytorch 把MNIST数据集转换成图片和txt的方法
May 20 Python
Python FTP两个文件夹间的同步实例代码
May 25 Python
详解Python3 对象组合zip()和回退方式*zip
May 15 Python
Python检查 云备份进程是否正常运行代码实例
Aug 22 Python
安装python及pycharm的教程图解
Oct 10 Python
python列表的逆序遍历实现
Apr 20 Python
python turtle绘图
May 04 Python
利用Python脚本写端口扫描器socket,python-nmap
Jul 23 Python
浅谈Python协程asyncio
Jun 20 #Python
Python3接口性能测试实例代码
Jun 20 #Python
使用Djongo模块在Django中使用MongoDB数据库
python自动计算图像数据集的RGB均值
详解如何用Python实现感知器算法
python中24小时制转换为12小时制的方法
Jun 18 #Python
用Python selenium实现淘宝抢单机器人
You might like
mysql总结之explain
2012/02/27 PHP
探讨Smarty中如何获取数组的长度以及smarty调用php函数的详解
2013/06/20 PHP
Yii不依赖Model的表单生成器用法实例
2014/12/04 PHP
php中JSON的使用方法
2015/04/30 PHP
深入浅析PHP7.0新特征(五大新特征)
2015/10/29 PHP
用js怎么把&字符换成"&amp:"
2006/10/19 Javascript
jquery 表格分页等操作实现代码(pagedown,pageup)
2010/04/11 Javascript
禁止选中文字兼容IE、Chrome、FF等
2013/09/04 Javascript
jq实现酷炫的鼠标经过图片翻滚效果
2014/03/12 Javascript
JavaScript实现选择框按比例拖拉缩放的方法
2015/08/04 Javascript
JS实现的Select三级下拉菜单代码
2015/08/20 Javascript
50 个 jQuery 插件可将你的网站带到另外一个高度
2016/04/26 Javascript
js与jquery正则验证电子邮箱、手机号、邮政编码的方法
2016/07/04 Javascript
JSON 必知必会 观后记
2016/10/27 Javascript
Javascript this 函数深入详解
2016/12/13 Javascript
浅谈regExp的test方法取得的值变化的原因及处理方法
2017/03/01 Javascript
vue项目中监听手机物理返回键的实现
2020/01/18 Javascript
Vue过渡效果之CSS过渡详解(结合transition,animation,animate.css)
2020/02/05 Javascript
原生JavaScript实现轮播图
2021/01/10 Javascript
[02:41]DOTA2英雄基础教程 冥魂大帝
2014/01/16 DOTA
用Python实现QQ游戏大家来找茬辅助工具
2014/09/14 Python
为python设置socket代理的方法
2015/01/14 Python
Python3实现从指定路径查找文件的方法
2015/05/22 Python
利用python获取当前日期前后N天或N月日期的方法示例
2017/07/30 Python
用python制作游戏外挂
2018/01/04 Python
Python实现修改文件内容的方法分析
2018/03/25 Python
python中sys模块是做什么用的
2020/08/16 Python
学生拾金不昧表扬信
2014/01/21 职场文书
四年大学生活的自我评价范文
2014/02/07 职场文书
《再见了,亲人》教学反思
2014/02/26 职场文书
2014卖家双十一活动策划书
2014/09/29 职场文书
给numpy.array增加维度的超简单方法
2021/06/02 Python
idea搭建可运行Servlet的Web项目
2021/06/26 Java/Android
SSM VUE Axios详解
2021/10/05 Vue.js
CSS3实现指纹特效代码
2022/03/17 HTML / CSS
java中为什么说子类的构造方法默认访问的是父类的无参构造方法
2022/04/13 Java/Android