我的编程空间,编程开发者的网络收藏夹
学习永远不晚

编码-2

短信预约 -IT技能 免费直播动态提醒
省份

北京

  • 北京
  • 上海
  • 天津
  • 重庆
  • 河北
  • 山东
  • 辽宁
  • 黑龙江
  • 吉林
  • 甘肃
  • 青海
  • 河南
  • 江苏
  • 湖北
  • 湖南
  • 江西
  • 浙江
  • 广东
  • 云南
  • 福建
  • 海南
  • 山西
  • 四川
  • 陕西
  • 贵州
  • 安徽
  • 广西
  • 内蒙
  • 西藏
  • 新疆
  • 宁夏
  • 兵团
手机号立即预约

请填写图片验证码后获取短信验证码

看不清楚,换张图片

免费获取短信验证码

编码-2

最近在socket中遇到了一个偶现bug,那就是与websocket建立连接后,进行数据传输后,在linux平台的终端下用socket_read()读取出来后,再用echo
打印出来的就是乱码。因为我做的只是一个数据中转,而另一端的C++则是用字节判断,而不是用字符串判断,而浏览器端的编码是utf-8,不知道为何会这样。这个问题在这个项目于结束后,终于有时间来纠结这个问题。当然,在一起的纠结的还有python的编码。这次就先说一说python的编码问题。

python编码问题的继续

之前的一篇文章对一些基本的python编码问题做了比较表面的解释,有兴趣的可以点击这里去看一下我对python编码的基础理解。好了,下面先提出我碰到的问题。

一个需要细思的例子

# windows 10 powershell
>>> u'知乎'
u'\u77e5\u4e4e'
>>> u'知乎'.encode('utf-8')
'\xe7\x9f\xa5\xe4\xb9\x8e'
>>> u'知乎'.encode('gbk')
'\xd6\xaa\xba\xf5'
>>> '知乎' #这个地方的编码被power shelll自己处理了
'\xd6\xaa\xba\xf5'

# sublime 3 REPL python
>>> u'知乎'
u'\u77e5\u4e4e'
>>> u'知乎'.encode('utf-8')
'\xe7\x9f\xa5\xe4\xb9\x8e'
>>> u'知乎'.encode('gbk')
'\xd6\xaa\xba\xf5'
>>> '知乎' #这个地方的编码被REPL自己处理了
'\xe7\x9f\xa5\xe4\xb9\x8e'

在上面两个例子的最后一行,可以看出在不同的shell下,这两个汉字的说明在解释器解释这个汉字字符串的时候是不同的。这个问题在stackoverflow,上有很好的解释。


解释 进度1

在进一步进行解释前,需要对 python 中的 ''u'' 进行详细的解释,在这个例子中我们就以 鐭ヤ箮 这个词来进行解释。

#windows 10 powershell 
>>>import sys
>>>sys.stdout.encoding
'cp936'
>>>'a'
'a'
>>>'鐭ヤ箮'
'\xe7\x9f\xa5\xe4\xb9\x8e'
>>> u'鐭ヤ箮'
u'\u942d\u30e4\u7bae'
>>>u'\u942d\u30e4\u7bae'.encode('ascii')
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
UnicodeEncodeError: 'ascii' codec can't encode characters in position 0-2: ordinal not in range(128)
>>>u'\u0047'.encode('ascii')
G

上面的这个例子,如果仔细思考的话,是可以引申出很多问题的。

第一个问题,汉字这个汉字是如何显示到屏幕上的,解释器又是如何处理这个汉字的,才使得最后解析出来的是一个点阵获取码。首先无论是怎样的方式输出的汉字(复制粘贴也好,直接用输入法也好),机器最终都是以点阵获取码(就是一段特殊的16进制数字)的形式去调用所拥有的点阵库,点阵库中的每一个汉字有他自己的特殊的点阵方式。当然这里的是点阵字库而不是矢量字库。

第二个问题是如果说python2中默认的编码方式是ascii,那么非英文字符按理来说是不能编码的 呀(因为ascii中只有英文字符)。其实这个说法本身是没有错的,而非英文字符还是要显示的,这个时候python就对这些非英文字符进行了不规范的处理,它会使用sys.stdout.encoding所显示的编码方案对当前显示的汉字进行编码,然后将这个汉字编码后的存储码输出而来。

第三个问题是 u'' 进行了什么样的处理。这个问题和第二个问题还是很有联系的,首先 u''python2 中表示的是对应字符的 unicode 码的形式,至于过程,则是使用当前的终端的编码方案对字符进行(decode)解码,然后再将解码后的所对应的 unicode 码显示出来。也就是说,u'' 这种形式,其实已经对字符进行了解码,所以如果采用 ascii 这种编码方案对超出编码范围的字符进行编码的话,是会出现上面所示的错误的。

解释 进度2

#the code below is under a file.py
#coding: utf-8
import sys
ed = sys.stdout.encoding
print '知乎'.decode('utf-8').encode(ed)

在进度1中,对python解释器对"", u""进行了比较详细的解释,我想大概也能解释了为什么有时候即使在文件头又coding:xxx这样的声明还是会出现各种各样的乱码。之所以会出现这样的乱码是因为在不同的终端下,ed是不一样的,而文件的编码保存方式却又是固定的,我觉得这样的设计不能说坏,但是至少现在来看确实不算是好的设计,在python3中到是在这方面进行了很大程度的改进,我觉得在这方面实现起来确实还不错。

回到话题,上面的这个文件,无论你在哪个平台下运行他都会呈现它原本的汉字。相反如果用下面这个样子的东西去测试,你也许就会发现所出出现的问题了。

print '知乎'

尾声

python2的编码问题其实早已经出现好久,一开始我只是解决了乱码的问题,后来在各种终端下测试的时候,发现了这样那样的问题,我觉得这真的还是蛮胃疼的,每次都得直接google错误,真的不是一个长久之计,遂花时间研究了一下编码。每次重新研究一次,总是会得到新的体验。
编码这个范畴真的还是蛮大的,有幸能在早期纠结于此。

pep-0263

这样的声明#coding: utf-8的意义,于此。

This PEP proposes to introduce a syntax to declare the encoding of

a Python source file. The encoding information is then used by the
Python parser to interpret the file using the given encoding. Most
notably this enhances the interpretation of Unicode literals in
the source code and makes it possible to write Unicode literals
using e.g. UTF-8 directly in an Unicode aware editor.

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

编码-2

下载Word文档到电脑,方便收藏和打印~

下载Word文档

猜你喜欢

编码-2

最近在socket中遇到了一个偶现bug,那就是与websocket建立连接后,进行数据传输后,在linux平台的终端下用socket_read()读取出来后,再用echo打印出来的就是乱码。因为我做的只是一个数据中转,而另一端的C++则是
2023-01-31

java编码规范(2) (转)

java编码规范(2) (转)[@more@]Java 编码规范(2)XML:namespace prefix = o ns = "urn:schemas-microsoft-com:Office:office" />翻译:王士勇(转载请保
2023-06-03

【JDBC】编程(2)-

实现模糊查询(以“查哪个用户的密码中的第二个字符为‘a’为例)......  import java.sql.*;public class DBUtil { /** * 工具类的构造方
【JDBC】编程(2)-
2017-06-28

Python 2与Python 3版本和编码的对比

一、版本对比 首先要说的是,Python的版本,目前主要分为两大类: Python 2.x的版本的,被称为Python2:是目前用的最广泛的,比如Python 2.7.3。 Python 3.x的版本的,被称为Python3:是最新的版本的
2022-06-04

编码 5 分钟,命名 2 小时?编程中头疼的事情:命名

好的命名即是注释,别人一看到你的命名就知道你的变量、方法或者类是做什么的! 好的命名对于其他人(包括你自己)理解你的代码有着很大的帮助!

Centos 编译安装Python 2.

Linux 系统是自带python的. 但是一般的版本都比较低  (CentOS5.6 带的python2.4版本)如果需要使用高版本的python 则需要自己 编译并安装编译python 前需要先安装 编译环境使用  yum instal
2023-01-31

Vue3 用组合编写更好的代码:灵活的参数(2/5)

本节,介绍一种模式,可以让我即可以使用 ref,又可以不使用,从而让组件更具有灵活性。

编写兼容 Python 2.x 和 3.

编写兼容Python2.x与3.x代码当我们正处于Python 2.x到Python 3.x的过渡期时,你可能想过是否可以在不修改任何代码的前提下能同时运行在Python 2和3中。这看起来还真是一个合理的诉求,但如何开始呢?哪些Pytho
2023-01-31

Go 2 泛型:编写更智能、适用于多种类型的代码

虽然泛型是一个强大的特性,但它们并不总是最佳解决方案。有时,简单的接口或具体类型更为合适。关键是明智地使用泛型,在代码重用和类型安全方面提供明显的好处时使用。
泛型接口Go2024-11-28

2. Python3源码—浮点对象

2.1. 浮点对象浮点对象是“定长对象”。2.1.1. Python中的创建Python中浮点对象创建最重要的方法为PyFloat_FromDouble,如下Python语句最终会调用到PyFloat_FromDouble:a = 1.23
2023-01-31

Vue 2 模版编译流程详解

到此我们应该了解了 vue 是如何打包构建将模板编译为渲染函数的,有了渲染函数后,只需要将渲染函数的 this 指向组件实例,即可和组件的响应式数据绑定。

Python基础2-Python中文乱码

转自:https://blog.csdn.net/apache0554/article/details/53889253前言:中文编码问题一直是程序员头疼的问题,而Python2中的字符编码足矣令新手抓狂。本文将尽量用通俗的语言带大家彻底的
2023-01-30

2.leetcode唯一的摩斯密码

1.题目International Morse Code defines a standard encoding where each letter is mapped to a series of dots and dashes, as
2023-01-31

python核心编程2 第六章 练习

6-2. 字符串标识符.修改例 6-1 的 idcheck.py 脚本,使之可以检测长度为一的标识符,并且可以识别 Python 关键字,对后一个要求,你可以使用 keyword 模块(特别是 keyword.kelist)来辅助 1 im
2023-01-30

python核心编程2 第九章 练习

9–1. 文件过滤. 显示一个文件的所有行, 忽略以井号( # )开头的行. 这个字符被用做Python , Perl, Tcl, 等大多脚本文件的注释符号.附加题: 处理不是第一个字符开头的注释.1 filename = input("输
2023-01-30

python核心编程2 第十章 练习

10-6.改进的open()。为内建的open()函数创建一个封装。使得成功打开文件后,返回文件句柄:若打开失败则返回给调用者None,而不是生成一个异常。这样你打开文件就不需要额外的异常处理语句。 1 def openfile(file)
2023-01-30

编程热搜

  • Python 学习之路 - Python
    一、安装Python34Windows在Python官网(https://www.python.org/downloads/)下载安装包并安装。Python的默认安装路径是:C:\Python34配置环境变量:【右键计算机】--》【属性】-
    Python 学习之路 - Python
  • chatgpt的中文全称是什么
    chatgpt的中文全称是生成型预训练变换模型。ChatGPT是什么ChatGPT是美国人工智能研究实验室OpenAI开发的一种全新聊天机器人模型,它能够通过学习和理解人类的语言来进行对话,还能根据聊天的上下文进行互动,并协助人类完成一系列
    chatgpt的中文全称是什么
  • C/C++中extern函数使用详解
  • C/C++可变参数的使用
    可变参数的使用方法远远不止以下几种,不过在C,C++中使用可变参数时要小心,在使用printf()等函数时传入的参数个数一定不能比前面的格式化字符串中的’%’符号个数少,否则会产生访问越界,运气不好的话还会导致程序崩溃
    C/C++可变参数的使用
  • css样式文件该放在哪里
  • php中数组下标必须是连续的吗
  • Python 3 教程
    Python 3 教程 Python 的 3.0 版本,常被称为 Python 3000,或简称 Py3k。相对于 Python 的早期版本,这是一个较大的升级。为了不带入过多的累赘,Python 3.0 在设计的时候没有考虑向下兼容。 Python
    Python 3 教程
  • Python pip包管理
    一、前言    在Python中, 安装第三方模块是通过 setuptools 这个工具完成的。 Python有两个封装了 setuptools的包管理工具: easy_install  和  pip , 目前官方推荐使用 pip。    
    Python pip包管理
  • ubuntu如何重新编译内核
  • 改善Java代码之慎用java动态编译

目录