[读书笔记]流畅的python-文本和字节序列
流畅的python-文本和字节序列
字符和字节
字符
“字符”的最佳定义是unicode字符,从python3的str对象中获取的元素是unicode字符,相当于从py2的unicode对象中获取的元素,而不是从py2的str对象中获取的原始字节序列。
字符的表示和具体的字节表述
- 字符的表示,即码位,在unicode标准中以4-6个十六进制数字表示。
- 字符的具体表述取决于所用的编码。如utf-8,utf-16LE
字节
python3中引入了不可变bytes类型和可变bytearray类型。bytes和bytearray对象的各个元素是介于0-255间的整数(1byte)。切片也是同一类型的二进制序列。
字节的字面量表示
- 可打印的ASCII范围内的字节,使用ASCII字符本身。
- 制表符、换行符、回车符和 \ 对应的字节,使用转义序列 \t、\n、\r 和 \。
- 其他字节的值,使用十六进制转义序列(例如,\x00 是空字节)。
byte的构造
- bytes.fromhex()
- 一个 str 对象和一个 encoding 关键字参数。
- 一个可迭代对象,提供 0~255 之间的数值。
- 一个实现了缓冲协议的对象(如 bytes、bytearray、memoryview、array.array);此时,把源对象中的字节序 列复制到新建的二进制序列中。
基本的编解码器
- Latin1:一种重要的编码,是其他编码的基础,例如 cp1252 和 Unicode(注意,latin1 与 cp1252 的字节值是一样的,甚至连码位也相同)。
- cp1252 :Microsoft 制定的 latin1 超集,添加了有用的符号,例如弯引号和€(欧元);有些 Windows 应用把它称为“ANSI”,但它并不是 ANSI 标准。
- cp437:IBM PC 最初的字符集,包含框图符号。与后来出现的 latin1 不兼容。
- gb2312:用于编码简体中文的陈旧标准;这是亚洲语言中使用较广泛的多字节编码之一。
- utf-8: 目前 Web 中最常见的 8 位编码; 与 ASCII 兼容(纯 ASCII 文本是有效的 UTF-8 文 本)。
编码问题
处理UnicodeEncodeError
可以在enocode是指定errors=xxx
>>> city = 'São Paulo' >>> city.encode('utf_8') b'S\xc3\xa3o Paulo' >>> city.encode('utf_16') b'\xff\xfeS\x00\xe3\x00o\x00 \x00P\x00a\x00u\x00l\x00o\x00' >>> city.encode('iso8859_1') b'S\xe3o Paulo' >>> city.encode('cp437') Traceback (most recent call last): File "<stdin>", line 1, in <module> File "/.../lib/python3.4/encodings/cp437.py", line 12, in encode return codecs.charmap_encode(input,errors,encoding_map) UnicodeEncodeError: 'charmap' codec can't encode character '\xe3' in position 1: character maps to <undefined> >>> city.encode('cp437', errors='ignore') b'So Paulo' >>> city.encode('cp437', errors='replace') b'S?o Paulo' >>> city.encode('cp437', errors='xmlcharrefreplace') ➏ b'São Paulo'
处理UnicodeDecodeError
指定errors,如:
octets.decode(‘utf_8’, errors=‘replace’)
如何找出字节序列的编码
统一字符编码侦测包 Chardet,,它能 识别所支持的 30 种编码。Chardet 是一个 Python 库,可以在程序中使用,不过它也提供了 命令行工具 chardetect。
BOM:鬼符
UTF-16 编码的序列开头有几个额外的字节b’\xff\xfe’。这就是 BOM,即字节序标记(byte-order mark),指明编码时使用 Intel CPU 的小字节序。
在小字节序设备中,各个码位的最低有效字节在前面:字母 ‘E’ 的码
位是 U+0045(十进制数 69),在字节偏移的第 2 位和第 3 位编码为 69和 0。
在大字节序 CPU 中,编码顺序是相反的;‘E’ 编码为 0 和 69。
UTF-8 的一大优势是,不管设备使用哪种字节序,生成的字节序列始终一致,因此不需要 BOM。
尽管如此,某些Windows 应用(尤其是 Notepad)依然会在 UTF-8 编码的文件中添加
BOM;而且,Excel 会根据有没有 BOM 确定文件是不是 UTF-8 编码,
否则,它假设内容使用 Windows 代码页(codepage)编码。
处理文本文件
处理文本的最佳实践是“Unicode 三明治”。 意思是,要尽早把输入(例 如读取文件时)的字节序列解码成字符串。不要依赖默认编码.
unicode规范化(比较和排序)
问题:因为 Unicode 有组合字符(变音符号和附加到前一个字符上的记号,打印时作为一个整 体),所以字符串比较起来很复杂。
方法:使用 unicodedata.normalize 函数提供的 Unicode 规范化。
** 大小写折叠**
大小写折叠其实就是把所有文本变成小写,再做些其他转换。这个功能由 str.casefold() 方法(Python 3.3 新增)支持。
规范化文本匹配函数
nfc_equal 和 fold_equal
unicode文本排序
方法一:
在 Python 中,非 ASCII 文本的标准排序方式是使用 locale.strxfrm 函数,根据 locale 模块的文档,这 个函数会“把字符串转换成适合所在区域进行比较的形式”。
方法二:
使用PyUCA库
PyUCA 没有考虑区域设置。如果想定制排序方式,可以把自定义的排序表路径传给 Collator() 构造方法。PyUCA 默认使用项目自带的 allkeys.txt(https://github.com/jtauber/pyuca),这就是 Unicode 6.3.0 的“Default Unicode Collation Element Table”(http://www.unicode.org/Public/UCA/6.3.0/allkeys.txt)的副本。
Unicode数据库
Unicode 标准提供了一个完整的数据库(许多格式化的文本文件),不仅包括码位与字符 名称之间的映射,还有各个字符的元数据,以及字符之间的关系。例如,Unicode 数据库 记录了字符是否可以打印、是不是字母、是不是数字,或者是不是其他数值符号。字符串 的 isidentifier、isprintable、isdecimal 和 isnumeric 等方法就是靠这些信息作 判断的。 str.casefold 方法也用到了 Unicode 表中的信息。 unicodedata 模块中有几个函数用于获取字符的元数据。例如,字符在标准中的官方名称是不是组合字符(如结合波形符构成的变音符号等),以及符号对应的人类可读数值(不是码位)。
注:re 模块对 Unicode 的支持并不充分。PyPI 中有个新开发的 regex 模块,它的最终目的是取代 re 模块,以提供更好的 Unicode 支持。
支持字符串和字节序列的双模式API
re和os模块中的一些函数能接受字符串或字节序列
正则匹配:re
如果使用字节序列构建正则表达式,\d 和 \w 等模式只能匹配 ASCII 字符;相比之下,如果是字符串模式,就能匹配 ASCII 之外的 Unicode 数字或字母。
前两个正则表达式是字符串类型。 后两个正则表达式是字节序列类型。
os函数中的字符串和字节序列
GNU/Linux 内核不理解 Unicode,为了规避这个问题,os 模块中的所有函数、文件名或路径名参数既能使用字符串,也能 使用字节序列。如果这样的函数使用字符串参数调用,该参数会使用 sys.getfilesystemencoding() 得到的编解码器自动编码,然后操作系统会使用相同 的编解码器解码。
- 流畅的python第四章文本和字节序列学习记录
- 流畅的Python第四章 文本和字节序列 第五章一等函数 第六章使用一等函数实现设计模式
- 流畅的Python 第4章: 文本和字节序列
- 《流畅的Python》读书笔记——Python文本和字节序列
- 流程的Python 第四章:文本和字节序列
- Python 文本和字节序列
- 5月5日读书笔记——流畅的python
- 流畅的python——4月18日读书笔记
- Python读书笔记009:文本统计
- 流畅的python第二章序列构成的数组学习记录
- 4月25日读书笔记——流畅的python
- Python学习笔记015——序列(字节数组 bytearray)
- IDA.【转】5.IDA-文本搜索、二进制搜索(16进制字节序列)、替换16进制
- Python数据类型之“文本序列(Text Sequence)”
- [读书笔记]流畅的Python(Fluent Python)
- 流畅的python第十章序列的修改,散列和切片学习记录
- Python学习笔记015——序列(字节数组 bytearray)
- 5月6日读书笔记——流畅的python
- 流畅的python:序列构成的数组-Part1
- 4-24日读书笔记——流畅的python