python版本坑:md5例子(python2与python3中md5区别)


Posted in Python onJune 20, 2017

起步

对于一些字符,python2和python3的md5加密出来是不一样的.

# python2.7
pwd = "xxx" + chr(163) + "fj"
checkcode = hashlib.md5(pwd).hexdigest()
print checkcode # ea25a328180680aab82b2ef8c456b4ce

# python3.6
pwd = "xxx" + chr(163) + "fj"
checkcode = hashlib.md5(pwd.encode("utf-8")).hexdigest()
print(checkcode) # b517e074034d1913b706829a1b9d1b67

按代码差异来将,就是在python3中需要对字符串进行 encode 操作,如果没有则会报错:

checkcode = hashlib.md5(pwd).hexdigest()
TypeError: Unicode-objects must be encoded before hashing

这是因为加密时需要将字符串转化为 bytes 类型,3默认编码是 utf-8 .所以我用utf-8进行解码.

分析

如果字符串中没有 chr(163) ,那么两个版本结果是一致的,也就是说问题出在这个chr(163)中:

# python2.7
>>> chr(163)
'\xa3'

# python3.6
>>> chr(163)
'\xa3'

在这里说明通过 chr 得到的结果是一致的, 将它转为 bytes 类型看看:

# python2.7
>>> bytes(chr(163))
'\xa3'

# python3.6
>>> chr(163).encode()
b'\xc2\xa3'

python3中,在 num<128 的时候,使用 chr(num).encode('utf-8') 得到的是 一个 字符的ascii十六进制,而 num>128 的时候,使用 chr(num).encode('utf-8') 得到的是 两个 字节的ascii十六进制.

解决
改用 latin1 编码进行解码:

# python3.6
pwd = "xxx" + chr(163) + "fj"
checkcode = hashlib.md5(pwd.encode("latin1")).hexdigest()
print(checkcode)  # ea25a328180680aab82b2ef8c456b4ce

额外
为什么是 latin1 编码呢.答案还是挺有意思的.

先说chr函数,通过 help(chr) 可以查看:

chr(...)
  chr(i) -> Unicode character
  Return a Unicode string of one character with ordinal i; 0 <= i <= 0x10ffff.

意思是它返回Unicode编码中指定位置的一个字符.python3内部也是用Unicode表示左右字符,即str类型.而通过encode后会编码成 bytes 类型.

ascii编码中每个字符编码是一个byte,但只有1-127. 超过的部分128-255则属于 Extended ASCII ,python3 中默认的ascii中不包含这部分,所以如果执行 chr(163).encode("ascii") 就会报错 'ascii' codec can't encode character '\xa3' in position 3: ordinal not in range(128)

因此需要一个含有128-255中的部分字符的编码,且采用1个Byte固定大小编码,比如ISO 8859-1,也就是 latin1.当然还有其他编码如cp1252也包含这些字符的.

Python 相关文章推荐
python单链表实现代码实例
Nov 21 Python
17个Python小技巧分享
Jan 23 Python
python根据出生日期返回年龄的方法
Mar 26 Python
举例讲解Python中的list列表数据结构用法
Mar 12 Python
Python生成密码库功能示例
May 23 Python
Django中URL的参数传递的实现
Aug 04 Python
python实现通过flask和前端进行数据收发
Aug 22 Python
python集合常见运算案例解析
Oct 17 Python
如何解决安装python3.6.1失败
Jul 01 Python
python如何对链表操作
Oct 10 Python
pycharm 使用anaconda为默认环境的操作
Feb 05 Python
python之django路由和视图案例教程
Jul 26 Python
Python编程实现两个文件夹里文件的对比功能示例【包含内容的对比】
Jun 20 #Python
Python中表达式x += y和x = x+y 的区别详解
Jun 20 #Python
回调函数的意义以及python实现实例
Jun 20 #Python
Python处理Excel文件实例代码
Jun 20 #Python
python构建自定义回调函数详解
Jun 20 #Python
Python实现完整的事务操作示例
Jun 20 #Python
python3.4用循环往mysql5.7中写数据并输出的实现方法
Jun 20 #Python
You might like
php curl模拟post请求小实例
2013/11/13 PHP
PHP 登录完成后如何跳转上一访问页面
2014/01/14 PHP
CodeIgniter框架URL路由总结
2014/09/03 PHP
PHP实现统计所有字符在字符串中出现次数的方法
2017/10/17 PHP
PHP生成随机密码4种方法及性能对比
2020/12/11 PHP
js getElementsByTagName的简写方式
2010/06/27 Javascript
JS前端框架关于重构的失败经验分享
2013/03/17 Javascript
jquery的父、子、兄弟节点查找,节点的子节点循环方法
2016/12/07 Javascript
javascript实现循环广告条效果
2017/12/12 Javascript
JS实现json数组排序操作实例分析
2019/10/28 Javascript
D3.js 实现带伸缩时间轴拓扑图的示例代码
2020/01/20 Javascript
Vue解析剪切板图片并实现发送功能
2020/02/04 Javascript
vue自定义插件封装,实现简易的elementUi的Message和MessageBox的示例
2020/11/20 Vue.js
[01:01]青春无憾,一战成名——DOTA2全国高校联赛开启
2018/02/25 DOTA
Python urlopen 使用小示例
2008/09/06 Python
在 Django/Flask 开发服务器上使用 HTTPS
2014/07/03 Python
python文件操作整理汇总
2014/10/21 Python
python实现单线程多任务非阻塞TCP服务端
2017/06/13 Python
Python格式化字符串f-string概览(小结)
2019/06/18 Python
python绘制雪景图
2019/12/16 Python
Python列表list操作相关知识小结
2020/01/29 Python
keras .h5转移动端的.tflite文件实现方式
2020/05/25 Python
iHerb香港:维生素、补充剂和天然保健品
2017/08/01 全球购物
高中历史教学反思
2014/02/08 职场文书
《商鞅南门立木》教学反思
2014/02/16 职场文书
销售会计岗位职责
2014/03/15 职场文书
婚纱店策划方案
2014/05/22 职场文书
企业职业病防治方案
2014/05/29 职场文书
2014年化妆品销售工作总结
2014/12/01 职场文书
2014年法院个人工作总结
2014/12/17 职场文书
博士论文答辩开场白
2015/06/01 职场文书
张思德观后感
2015/06/09 职场文书
春晚观后感
2015/06/11 职场文书
PyTorch梯度裁剪避免训练loss nan的操作
2021/05/24 Python
Django操作cookie的实现
2021/05/26 Python
漫画「请问您今天要来点兔子吗?」最新杂志彩页公开
2022/03/24 日漫