对于人类能够识别的字符,计算机会根据某一对应关系将其转换为二进制形式进行保存。这个对应关系就是字符编码表,即什么样的字符对应什么样的二进制编码。这种字符编码表往往是多种多样的,因此,如果我们想要将一个未知编码的二进制文件转换为可读文本进行显示,就需要考其使用的是什么类型的字符编码。关于字符编码的进一步介绍见文章字符集和字符编码

现实中,往往根据各种字符编码的特征字符来猜测当前文件使用的是什么类型的字符编码。但是许多字符对于不同字符编码是通用的,区别在于每种编码可能使用不同的字节序列来存储同一字符,根据这一特性再进一步处理。在Python中,chardet库能够提供了实现字符编码自动检测的函数。chardet支持绝大部分常见字符编码的识别,其官方仓库见:chardet。chardet安装指令如下:

pip install chardet

1 使用

基础使用

chardet提供detect函数接口实现字符编码的自动检测。detect函数接受一个参数,即非Unicode字符串。它返回一个字典,其中包含自动检测到的字符编码和范围为0到1的置信度,还有语言类型。

# 导入库
import urllib.request
import chardet
# 读取网站
rawdata = urllib.request.urlopen('http://baidu.com/').read()
# 可以看到使用的是ascii编码
chardet.detect(rawdata)
{'encoding': 'ascii', 'confidence': 1.0, 'language': ''}
# 读取网站
rawdata = urllib.request.urlopen('http://en.people.cn/').read()
# 可以看到使用的是utf-8编码
chardet.detect(rawdata)
{'encoding': 'utf-8', 'confidence': 0.99, 'language': ''}
# 创建utf-8字节类型数据
data = bytes('hello, world', encoding='utf-8')
print(data)
chardet.detect(data)
b'hello, world'

{'encoding': 'ascii', 'confidence': 1.0, 'language': ''}
# bytes类型可以直接通过python的decode函数进行解码
data.decode('ascii')
'hello, world'
# 创建utf-8字节类型数据,这里可以看到utf-8是最高效的编码方式。
data = bytes('hello, world!你好世界!', encoding='utf-8')
print(data)
chardet.detect(data)
b'hello, world!\xe4\xbd\xa0\xe5\xa5\xbd\xe4\xb8\x96\xe7\x95\x8c\xef\xbc\x81'

{'encoding': 'utf-8', 'confidence': 0.9690625, 'language': ''}
# bytes类型可以直接通过python的decode函数进行解码
data.decode('utf-8')
'hello, world!你好世界!'
data = bytes('你好世界', encoding='GBK')
# 识别可能错误
chardet.detect(data)
{'encoding': None, 'confidence': 0.0, 'language': None}
# 需要更丰富的字符数据提高识别率
data = bytes('你好世界,你好', encoding='GBK')
chardet.detect(data)
{'encoding': 'GB2312', 'confidence': 0.99, 'language': 'Chinese'}

大量文本识别

如果您正在处理大量文本,您可以调用UniversalDetector,以加快识别速度。下面的代码首先创建一个UniversalDetector对象,然后对大型文本分块识别,每个文本块用其检测方法feed。如果检测器达到最小置信阈值,它将设置detector.done为True,进而输出当前文本的字符编码。

import urllib.request
from chardet.universaldetector import UniversalDetector usock = urllib.request.urlopen('http://baidu.com/')
detector = UniversalDetector()
for line in usock.readlines():
detector.feed(line)
if detector.done: break
detector.close()
usock.close()
print(detector.result)
{'encoding': 'ascii', 'confidence': 1.0, 'language': ''}

对于多个文件或多个字符串,也可以使用UniversalDetector加快识别速度。


from chardet.universaldetector import UniversalDetector texta = bytes('hello, world', encoding='utf-8')
textb = bytes('你好世界,你好', encoding='GBK') detector = UniversalDetector()
for data in [texta,textb]:
# 检测器重置
detector.reset()
detector.feed(data)
if detector.done: break
detector.close()
print(detector.result)
{'encoding': 'ascii', 'confidence': 1.0, 'language': ''}
{'encoding': 'GB2312', 'confidence': 0.99, 'language': 'Chinese'}

UnicodeDammit的使用

UnicodeDammit是beautifulsoup的内置库, 用于猜测字符编码。在UnicodeDammit中集成了chardet模块使得我们可以快速获取字符编码。

from bs4 import UnicodeDammit

data = bytes('你好世界,你好', encoding='GBK')
dammit = UnicodeDammit(data)
# 解码结果
print(dammit.unicode_markup)
# 打印编码结果
print(dammit.original_encoding)
# 或直接调用chardet
print(dammit.detector.chardet_encoding)
你好世界,你好
gb2312
GB2312

2 参考

[python] 基于chardet识别字符编码的更多相关文章

  1. python之旅:字符编码

    一 了解字符编码的知识储备 一 计算机基础知识 知识储备:cpu.内存.硬盘 二 文本编辑器存取文件的原理(nodepad++,pycharm,word) #1.打开编辑器就打开了启动了一个进程,是在 ...

  2. 用chardet判断字符编码的方法

    转自http://www.cnblogs.com/xiaowuyi/archive/2012/03/09/2387173.html 用chardet判断字符编码的方法   1.chardet下载与安装 ...

  3. python基础——6(字符编码,文件操作)

    今日内容: 1.字符编码: 人识别的语言与机器识别的语言转化的媒介 *****     2.字符与字节: 字符占多少字节,字符串转化 ***     3.文件操作: 操作硬盘中的一块区域:读写操作  ...

  4. python文件操作:字符编码与文件处理

    一.字符编码 二.文件处理 一.字符编码 储备知识点: 1. 计算机系统分为三层: 应用程序 操作系统 计算机硬件 2. 运行python程序的三个步骤 1. 先启动python解释器 2. 再将py ...

  5. python文件操作与字符编码

    知识内容: 1.文件对象与文件处理流程 2.基本操作 3.上下文管理 4.文件的修改与文件内光标的移动 5.字符编码 一.文件对象与文件处理流程 1.文件对象 (1)文件分类 按文件中数据的组织形式可 ...

  6. python(10)- 字符编码

    一 什么是编码? 基本概念很简单.首先,我们从一段信息即消息说起,消息以人类可以理解.易懂的表示存在.我打算将这种表示称为“明文”(plain text).对于说英语的人,纸张上打印的或屏幕上显示的英 ...

  7. python(4)- 字符编码

    一 什么是编码? 基本概念很简单.首先,我们从一段信息即消息说起,消息以人类可以理解.易懂的表示存在.我打算将这种表示称为“明文”(plain text).对于说英语的人,纸张上打印的或屏幕上显示的英 ...

  8. 小白的Python之路 day1 字符编码

    字符编码 python解释器在加载 .py 文件中的代码时,会对内容进行编码(默认ascill) ASCII(American Standard Code for Information Interc ...

  9. Python 入门基础6 --字符编码、文件操作1

    今日内容: 1.字符编码 2.字符与字节 3.文件操作 一.字符编码 了解: cpu:将数据渲染给用户 内存:临时存放数据,断电消失 硬盘:永久存放数据,断电后不消失 1.1 什么是编码? 人类能够识 ...

随机推荐

  1. OnionArch - 采用DDD+CQRS+.Net 7.0实现的洋葱架构

    博主最近失业在家,找工作之余,看了一些关于洋葱(整洁)架构的资料和项目,有感而发,自己动手写了个洋葱架构解决方案,起名叫OnionArch.基于最新的.Net 7.0 RC1, 数据库采用Postgr ...

  2. SpringMVC访问不到默认页的问题。

    在web.xml中配置了 <welcome-file-list> <welcome-file>index.html</welcome-file> </welc ...

  3. Dropout----Dropout来源

    目录 一.简单介绍及公式 二.为什么dropout有效-原因定性分析 2.1 ensemble论 2.1.1 ensemble 2.1.2 动机:联合适应(co-adapting) 思考: 2.1.3 ...

  4. Linux实战笔记_ 如何远程访问Kali?

    注:基于2018年安装的kali版本. 启动ssh服务 /etc/init.d/ssh start 或 service ssh start #启动ssh服务 /etc/init.d/ssh statu ...

  5. LcdTools如何编写MIPI指令(初始化代码)

    在LcdTools帮助文档中查看MIPI读写指令描述,如下图 编写LCM初始化代码就是配置LCM Driver IC寄存器值,一般只需用MipiWrite()指令写参数即可:下面介绍MipiWrite ...

  6. 野火 STM32MP157 开发板内核和设备树的编译烧写

    一.环境 编译环境:Ubuntu 版本:18.4.6 交叉编译工具:arm-linux-gnueabihf-gcc 版本:7.4.1 开发板:STM32MP157 pro 烧写方式:STM32Cube ...

  7. 1.docker的基本使用

    1.简介 Docker 是一个开源的应用容器引擎,让开发者可以打包他们的应用以及依赖包到一个可移植的镜像中,然后发布到任何流行的 Linux或Windows操作系统的机器上,也可以实现虚拟化.容器是完 ...

  8. 修改api-server支持的NodePort端口映射范围

    创建svc资源报错显示:provided port is not in the valid range. The range of valid ports is 30000-32767 k8s集群默认 ...

  9. php 程序员进化之路

    1.目标明确 2.消除干扰 3.自我激励 鸟哥 --2018年11月17日php年会

  10. 24、编写一个函数void replace(char *str1,char *str2,int i,int j),将字符串中str1中的第i个字符开始到j个字符结束的位置替换为str2.

    /* 编写一个函数void replace(char *str1,char *str2,int i,int j),将字符串中str1中的第i个字符开始到j个字符结束的位置替换为str2. */ #in ...