Python 3.4 有什么新变化
- 作者:
- R. David Murray <rdmurray@bitdance.com> (Editor)
这篇文章介绍了 Python 3.4 相比 3.3 增加的新特性。 Python 3.4 发布于 2014 年 3 月 16 日。 对于完整的细节,请参见 更新日志 [https://docs.python.org/3.4/whatsnew/changelog.html]。
参见
PEP 429 [https://peps.python.org/pep-0429/] — Python 3.4 发布计划
摘要 - 发布重点
新的语法特性:
- Python 3.4 中没有增加新的语法特性。
其他的新特性
新创建的文件描述符是不可继承的 ( PEP 446 [https://peps.python.org/pep-0446/])。
对应 隔离模式 的命令行选项 (bpo-16499 [https://bugs.python.org/issue?@action=redirect&bpo=16499])。
针对非文本编码格式的 编解码器处理方式的改进 (多个相关问题)。
针对导入系统的 ModuleSpec 类型 ( PEP 451 [https://peps.python.org/pep-0451/])。 (将影响导入器的作者。)
marshal
格式已被改进为 更为紧凑与高效 (bpo-16475 [https://bugs.python.org/issue?@action=redirect&bpo=16475])。
新的库模块:
asyncio
: 针对异步 IO 的新版暂定 API ( PEP 3156 [https://peps.python.org/pep-3156/])。ensurepip
: 引导设置 pip 安装器 ( PEP 453 [https://peps.python.org/pep-0453/])。enum
: 对枚举类型的支持 ( PEP 435 [https://peps.python.org/pep-0435/])。pathlib
: 面向对象的文件系统路径 ( PEP 428 [https://peps.python.org/pep-0428/])。selectors
: 高层级且高效率的 I/O 复用,在select
模块的基础之上建立(为 PEP 3156 [https://peps.python.org/pep-3156/] 的组成部分)。statistics
: 基础 数字领域稳定统计库 ( PEP 450 [https://peps.python.org/pep-0450/])。tracemalloc
: 追踪 Python 内存分配 ( PEP 454 [https://peps.python.org/pep-0454/])。
显著改进的库模块:
functools
中的 单一调度泛型函数 ( PEP 443 [https://peps.python.org/pep-0443/])。新的
pickle
协议 4 ( PEP 3154 [https://peps.python.org/pep-3154/])。multiprocessing
现在包含 一个避免在 Unix 上使用 os.fork 的选项 (bpo-8713 [https://bugs.python.org/issue?@action=redirect&bpo=8713])。email
增加新的子模块contentmanager
和新的子类型Message
(EmailMessage
) 用以 简化 MIME 处理 (bpo-18891 [https://bugs.python.org/issue?@action=redirect&bpo=18891])。inspect
和pydoc
模块现在能够自省更多种类的可调用对象,这改进了 Pythonhelp()
系统的输出。ipaddress
模块 API 已被声明为稳定状态
安全改进:
将新创建的文件描述符设为不可继承 ( PEP 446 [https://peps.python.org/pep-0446/]) 以避免将文件描述符泄露给子进程。
新增对应 隔离模式 的命令行选项。 (bpo-16499 [https://bugs.python.org/issue?@action=redirect&bpo=16499])。
现在
multiprocessing
具有 一个在 Unix 上避免使用 os.fork 的选项。 spawn 和 forkserver 更为安全因为它们会避免与子进程共享数据。在 Windows 上
multiprocessing
子进程将不再继承父进程的所有可继承句柄,而仅继承必需的几个。新增的
hashlib.pbkdf2_hmac()
函数可提供 PKCS#5 基于口令的密钥派生函数 2 [https://en.wikipedia.org/wiki/PBKDF2]。在
ssl
中对于 TLSv1.1 和 TLSv1.2 的支持。在
ssl
中对于 从 Windows 系统证书库获取证书的支持。ssl.SSLContext
类具有 大量改进。标准库中所有支持 SSL 的模块现在都支持服务器证书验证,包括主机名匹配 (
ssl.match_hostname()
) 和 CRL (Certificate Revocation Lists,参见ssl.SSLContext.load_verify_locations()
)。
CPython 实现的改进:
通过应用 PEP 442 [https://peps.python.org/pep-0442/],在大多数情况下 模块的 globals 在最终化期间将不再被设为 None (bpo-18214 [https://bugs.python.org/issue?@action=redirect&bpo=18214])。
Argument Clinic ( PEP 436 [https://peps.python.org/pep-0436/])。
请继续阅读有关针对用户的改变的完整清单,包括许多其他较小的改进、CPython 优化、弃用以及潜在的移植问题。
新的特性
PEP 453: 在 Python 安装版中对 PIP 的显式初始设置
默认对 pip 进行初始设置
新增的 ensurepip
模块(在 PEP 453 [https://peps.python.org/pep-0453/] 中定义)提供了一个在 Python 安装版和虚拟环境中初始设置 pip 安装器的标准跨平台机制。 包括在 Python 3.4.0 中的 pip
版本是 pip
1.5.4,未来的 3.4.x 维护发布版会将附带版本升级为创建候选发布版时的 pip
最新版本。
在默认情况下,将在所有平台上安装 pipX
和 pipX.Y
等命令(其中 X.Y 表示 Python 安装包的版本),并包括 pip
Python 包及其依赖。 在 Windows 中以及所有平台的虚拟环境中,还将安装不带版本号的 pip
命令。 在其他平台中,系统层级上不带版本号的 pip
命令通常是指向单独安装的 Python 2 版本。
pyvenv
命令行工具和 venv
模块可利用 ensurepip
模块在虚拟环境中准备好 pip
。 当使用命令行工具时,会默认安装 pip
,而当使用 venv
模块的 API 安装版时必须显式地安装 pip
。
对于 CPython 在 POSIX 系统上的源代码编译版,make install
和 make altinstall
命令默认会初始设置 pip
。 此行为可通过配置选项来控制,并通过 Makefile 选项来重写。
在 Windows 和 Mac OS X 上,现在 CPython 安装程序默认会将 pip
与 CPython 本身一同安装(用户可以在安装过程中选择不安装它)。 Window 用户需要选择执行 PATH
修改以使 pip
在命令行中默认可用,在其他情况下它仍然可以通过 Windows 版 Python 启动器以 py -m pip
的方式使用。
正如 在 PEP 中已讨论的 [https://peps.python.org/pep-0453/#recommendations-for-downstream-distributors] 那样平台打包者可以选择不默认安装这些命令,只需在它们被唤起时,能够提供有关如何在该平台上安装它们的简单清晰的指引(通常是使用系统的包管理器)。
备注
为了避免同时存在的 Python 2 和 Python 3 安装版之前的冲突,当 ensurepip
被直接唤起时默认只会初始设置带版本号的 pip3
和 pip3.4
命令 —— 需要添加 --default-pip
选项来请求设置不带版本号的 pip
命令。 pyvenv
和 Windows 安装程序会确保未限定版本的 pip
命令在环境中可用,并且 pip
始终可以通过 -m
选项开关而不是直接唤起以避免在具有多个 Python 安装版的系统中造成歧义。
文档更改
作为此项更改的一部分,文档的 安装 Python 模块 和 分发 Python 模块 章节已经完全重新设计,快速入门和 FAQ 文档也是如此。 大部分打包指南文档现在都已被移至由 Python Packaging Authority 维护的 Python Packaging User Guide [https://packaging.python.org] 以及相应的独立项目文档。
不过,由于目前迁移过程尚未完成,这些指南的旧版本仍然可通过 使用 setuptools 构建 C 和 C++ 扩展 和 使用 setuptools 构建 C 和 C++ 扩展 来访问。
参见
- PEP 453 [https://peps.python.org/pep-0453/] — Python 安装版中对 pip 的显式初始设置
- PEP 由Donald Stufft 和 Nick Coghlan 撰写,由 Donald Stufft,Nick Coghlan,Martin von Löwis 和 Ned Deily 实现。
PEP 446: 新创建的文件描述符将设为不可继承
PEP 446 [https://peps.python.org/pep-0446/] 将新创建的文件描述符设为 不可继承的。 通常,这就是应用程序所需要的行为:当启动一个新进程时,让当前打开的文件也在新进程里打开可能导致各种难以查找的程序错误以及潜在的安全问题。
不过,也存在一些需要继承行为的情况。 为了支持这些情况,可以使用以下的新增函数和方法:
参见
- PEP 446 [https://peps.python.org/pep-0446/] — 将新创建的文件描述符设为不可继承
- PEP 由 Victor Stinner 撰写并实现。
编解码器处理方式的改进
自首次被引入以来,codecs
模块始终是作为一个类型中立的动态编码和解码系统来运作的。 然而,它与 Python 文本模型,尤其是内置 str
、bytes
和 bytearray
类型上的限定类型的便捷方法的紧密耦合,在历史上掩盖了这一事实。
作为明晰情况的关键一步,现在 codecs.encode()
和 codecs.decode()
便捷函数在 Python 2.7、3.3 和 3.4 中都正确地写入了文档。 自 Python 2.4 以来这些函数即已存在于 codecs
模块中(并已被回归测试套件所覆盖),但在此前只能通过运行时自省才能发现。
不同于 str
, bytes
和 bytearray
上的便捷方法,codecs
的便捷函数同时支持 Python 2 和 Python 3 中的任意编解码器,而非仅限于 Unicode 文本编码格式(在 Python 3 中) 或 basestring
<-> basestring
转换(在 Python 2 中)。
在 Python 3.4 中,解释器能够识别标准库中提供的已知非文本编码格式并会在适当的时候引导用户找到这些通用型便捷函数:
- >>> b"abcdef".decode("hex")
- Traceback (most recent call last):
- File "<stdin>", line 1, in <module>
- LookupError: 'hex' is not a text encoding; use codecs.decode() to handle arbitrary codecs
- >>> "hello".encode("rot13")
- Traceback (most recent call last):
- File "<stdin>", line 1, in <module>
- LookupError: 'rot13' is not a text encoding; use codecs.encode() to handle arbitrary codecs
- >>> open("foo.txt", encoding="hex")
- Traceback (most recent call last):
- File "<stdin>", line 1, in <module>
- LookupError: 'hex' is not a text encoding; use codecs.open() to handle arbitrary codecs
在相关的改变中,只要在不破坏向下兼容性 的情况下是可行的,则在编码和解码操作期间引发的异常都会被包装在一个特定类型的链式异常中,该类型的名称与产生错误的相应编解码器一致:
- >>> import codecs
- >>> codecs.decode(b"abcdefgh", "hex")
- Traceback (most recent call last):
- File "usrlib/python3.4/encodings/hex_codec.py", line 20, in hex_decode return (binascii.a2b_hex(input), len(input))
- binascii.Error: Non-hexadecimal digit found
- The above exception was the direct cause of the following exception:
- Traceback (most recent call last):
- File "<stdin>", line 1, in <module>
- binascii.Error: decoding with 'hex' codec failed (Error: Non-hexadecimal digit found)
- >>> codecs.encode("hello", "bz2")
- Traceback (most recent call last):
- File "usrlib/python3.4/encodings/bz2_codec.py", line 17, in bz2_encode return (bz2.compress(input), len(input))
- File "usrlib/python3.4/bz2.py", line 498, in compress return comp.compress(data) + comp.flush()
- TypeError: 'str' does not support the buffer interface
- The above exception was the direct cause of the following exception:
- Traceback (most recent call last):
- File "<stdin>", line 1, in <module>
- TypeError: encoding with 'bz2' codec failed (TypeError: 'str' does not support the buffer interface)
最后,正如上面的例子所示,这些改进允许恢复非 Unicode 编解码器的便捷别名,这些别名在 Python 3.2 中已被恢复。 这意味着(举例来说)二进制数据到其十六进制表示形式的编码转换现在可以写成:
- >>> from codecs import encode, decode
- >>> encode(b"hello", "hex")
- b'68656c6c6f'
- >>> decode(b"68656c6c6f", "hex")
- b'hello'
在标准库中提供的二进制和文本转换操作详见 二进制转换 和 文字转换。
(由 Nick Coghlan 在 bpo-7475 [https://bugs.python.org/issue?@action=redirect&bpo=7475], bpo-17827 [https://bugs.python.org/issue?@action=redirect&bpo=17827], bpo-17828 [https://bugs.python.org/issue?@action=redirect&bpo=17828] 和 bpo-19619 [https://bugs.python.org/issue?@action=redirect&bpo=19619] 中贡献。)
PEP 451: 针对导入系统的 ModuleSpec 类型
PEP 451 [https://peps.python.org/pep-0451/] 提供了对模块相关信息的封装,导入机制将使用这些信息来加载它(即模块规范说明)。 这有助于简化导入的实现和几个导入相关的 API。 这一改动也是 某些未来导入相关改进 [https://mail.python.org/pipermail/python-dev/2013-November/130111.html] 的基石。
PEP 中面向公众的修改是完全向下兼容的。 并且,它们应当对除导入器开发者之外的其他所有人都可见。 主要查找器和加载器方法已被弃用,但它们将继续工作。 新的导入器应当使用 PEP 中描述的新方法。 现有的导入器应当被更新以实现这些新方法。 请参阅 弃用 一节获取应当被替代的方法及其替代物的列表。
其他语言特性修改
对Python 语言核心进行的小改动:
Unicode 数据库更新至 UCD 版本 6.3。
现在
min()
和max()
均接受一个 default 仅限关键字参数可被用来指定当它们要求值的可迭代对象中没有任何元素时要返回的值。 (由 Julian Berman 在 bpo-18111 [https://bugs.python.org/issue?@action=redirect&bpo=18111] 中贡献。)模块对象现在是 可弱引用的。
模块的
__file__
属性(以及相关的值)现在应当总是默认包含绝对路径,唯一的例外是当使用相对路径直接执行一个脚本时的__main__.__file__
。 (由 Brett Cannon 在 bpo-18416 [https://bugs.python.org/issue?@action=redirect&bpo=18416] 中贡献。)现在所有 UTF-* 编解码器(UTF-7 除外)在编码和解码期间都将拒绝替代符除非使用
surrogatepass
错误处理器,例外情况有 UTF-16 解码器(接受有效的替代符对)和 UTF-16 编码器(在编码非 BMP 字符时会产生替代符)。 (由 Victor Stinner, Kang-Hao (Kenny) Lu 和 Serhiy Storchaka 在 bpo-12892 [https://bugs.python.org/issue?@action=redirect&bpo=12892] 中贡献。)新增 German EBCDIC 编解码器
cp273
。 (由 Michael Bierenfeld 和 Andrew Kuchling 在 bpo-1097797 [https://bugs.python.org/issue?@action=redirect&bpo=1097797] 中贡献。)新增 Ukrainian 编解码器
cp1125
。 (由 Serhiy Storchaka 在 bpo-19668 [https://bugs.python.org/issue?@action=redirect&bpo=19668] 中贡献。)现在
bytes
.join() 和bytearray
.join() 接受任意缓冲区对象作为参数。 (由 Antoine Pitrou 在 bpo-15958 [https://bugs.python.org/issue?@action=redirect&bpo=15958] 中贡献。)现在
int
构造器接受任何具有__index__
方法的对象作为其 base 参数。 (由 Mark Dickinson 在 bpo-16772 [https://bugs.python.org/issue?@action=redirect&bpo=16772] 中贡献。)帧对象现在具有
clear()
方法用来从帧中清除所有对局部变量的引用。 (由 Antoine Pitrou 在 bpo-17934 [https://bugs.python.org/issue?@action=redirect&bpo=17934] 中贡献。)现在
memoryview
被注册为序列
,并支持reversed()
内置函数。 (由 Nick Coghlan 和 Claudiu Popa 在 bpo-18690 [https://bugs.python.org/issue?@action=redirect&bpo=18690] 和 bpo-19078 [https://bugs.python.org/issue?@action=redirect&bpo=19078] 中贡献。)作为对引入 Argument Clinic 以及对
inspect
和pydoc
模块的其他修改的结果,在各种场合下由help()
所报告的签名信息已获得修改和提升。现在
__length_hint__()
已成为正式语言规范的一部分 (参见 PEP 424 [https://peps.python.org/pep-0424/])。 (由 Armin Ronacher 在 bpo-16148 [https://bugs.python.org/issue?@action=redirect&bpo=16148] 中贡献。)
新增模块
asyncio
新增的 asyncio
模块(在 PEP 3156 [https://peps.python.org/pep-3156/] 中定义)为 Python 提供了一个标准的可插入事件循环模型,在标准库中提供了坚实的异步 IO 支持,并使得其他事件循环的实现与标准库和其他库的相互操作更为容易。
对于 Python 3.4,此模块被视为属于 provisional API。
参见
- PEP 3156 [https://peps.python.org/pep-3156/] — 异步 IO 支持的重启: "asyncio" 模块
- PEP 由 Guido van Rossum 领导编写和实现。
ensurepip
新增的 ensurepip
模块是用于 PEP 453 [https://peps.python.org/pep-0453/] 实现的主要基础设施。 在正常情况下最终用户不需要与此模块进行交互,但如果对安装版或虚拟环境的自动初始设置遭到拒绝则可使用它来手动初始设置 pip
。
ensurepip
包括了一个捆绑的 pip
副本,其版本更新时间即 CPython 发布包的第一个候选发布版的发布时间(此规则同样适用于维护发布版和新特性发布版)。 ensurepip
不会访问因特网。 如果安装版可以访问因特网,则在运行 ensurepip
之后可以使用所捆绑的 pip
来将 pip
升级为比所捆绑版本更高的版本。 (请注意这样得到的 pip
升级版本将被视为一个单独安装的软件包并且在 Python 被卸载时将不会被移除。)
该模块被命名为 ensurepip 是因为如果在已安装 pip
的情况下被调用,它将不做任何操作。 它还有一个 --upgrade
选项可以在当前已安装的 pip
版本比所捆绑的副本更旧的情况下安装所捆绑的 pip
副本。
enum
新增的 enum
模块(在 PEP 435 [https://peps.python.org/pep-0435/] 中定义)提供了枚举类型的标准实现,允许其他模块(如 socket
等)通过将含义不清晰的整数常量替换为可向下兼容的枚举值来提供更具信息量的错误消息和更好的调试支持。
参见
- PEP 435 [https://peps.python.org/pep-0435/] — 为 Python 标准库增加了 Enum 类型
- PEP 由 Barry Warsaw,Eli Bendersky 和 Ethan Furman 撰写 ,由 Ethan Furman 实现。
pathlib
新增的 pathlib
模块提供了代表文件系统路径的类,其语义适用于不同的操作系统。 路径类被划分为提供不带 I/O 的纯计算操作的 纯路径,以及继承自纯路径但提供 I/O 操作的 实体路径。
对于 Python 3.4,此模块被视为属于 provisional API。
参见
- PEP 428 [https://peps.python.org/pep-0428/] — pathlib 模块 — 面向对象的文件系统路径
- PEP 由 Antoine Pitrou 撰写并实现
selectors
新增的 selectors
模块(作为 PEP 3156 [https://peps.python.org/pep-3156/] 实现的一部分被创建)允许高层级且高效的 I/O 多路复用,它是在 select
模块的基础上构建的。
statistics
新增的 statistics
模块(在 PEP 450 [https://peps.python.org/pep-0450/] 中定义)直接在标准库中提供了一些核心统计功能。 该模块支持计算数据系列的平均值、中位数、模式、方差和标准差等。
参见
- PEP 450 [https://peps.python.org/pep-0450/] — 为标准库增加 statistics 模块
- PEP 由 Steven D'Aprano 撰写并实现。
tracemalloc
新增的 tracemalloc
模块(在 PEP 454 [https://peps.python.org/pep-0454/] 中定义)是用于追踪由 Python 所分配的内存块的调试工具。 它提供了以下信息:
追踪对象被分配所在的位置
按文件、按行统计python的内存块分配情况: 总大小、块的数量以及块平均大小。
对比两个内存快照的差异,以便排查内存泄漏
参见
- PEP 454 [https://peps.python.org/pep-0454/] — 新增 tracemalloc 模块用于追踪 Python 内存分配
- PEP 由 Victor Stinner 撰写并实现
改进的模块
abc
新增的函数 abc.get_cache_token()
可被用来获知何时使得受到对象图改变影响的缓存失效。 (由 Łukasz Langa 在 bpo-16832 [https://bugs.python.org/issue?@action=redirect&bpo=16832] 中贡献。)
新增的类型 ABC
以 ABCMeta
作为其元类。 使用 ABC
作为基类的效果实际上相当于指定 metaclass=abc.ABCMeta
,但其写法更简单也更易读。 (由 Bruno Dupuis 在 bpo-16049 [https://bugs.python.org/issue?@action=redirect&bpo=16049] 中贡献。)
aifc
现在 getparams()
方法将返回一个具名元组而不是普通元组。 (由 Claudiu Popa 在 bpo-17818 [https://bugs.python.org/issue?@action=redirect&bpo=17818] 中贡献。)
现在 aifc.open()
已支持上下文管理协议:当在 with
代码块中使用时,所返回对象的 close()
方法将在代码块结束时被自动调用。 (由 Serhiy Storchacha 在 bpo-16486 [https://bugs.python.org/issue?@action=redirect&bpo=16486] 中贡献。)
现在 writeframesraw()
和 writeframes()
方法将接受任意 bytes-like object。 (由 Serhiy Storchaka 在 bpo-8311 [https://bugs.python.org/issue?@action=redirect&bpo=8311] 中贡献。)
argparse
现在 FileType
类可接受 encoding 和 errors 参数,它们将被传递给 open()
。 (由 Lucas Maystre 在 bpo-11175 [https://bugs.python.org/issue?@action=redirect&bpo=11175] 中贡献。)
audioop
现在 audioop
可支持 24 位采样。 (由 Serhiy Storchaka 在 bpo-12866 [https://bugs.python.org/issue?@action=redirect&bpo=12866] 中贡献。)
新增的 byteswap()
函数可将大端序样本转换为小端序,并可反向转换。 (由 Serhiy Storchaka 在 bpo-19641 [https://bugs.python.org/issue?@action=redirect&bpo=19641] 中贡献。).) 所有 audioop
函数现在可接受任意 bytes-like object。 字符串将不被接受:它们在之前也不可用,现在它们将立即引发错误。 (由 Serhiy Storchaka 在 bpo-16685 [https://bugs.python.org/issue?@action=redirect&bpo=16685] 中贡献。)
base64
现在 base64
中的编码和解码函数在之前需要 bytes
或 bytearray
实例的场合下均接受任意 bytes-like object。 (由 Nick Coghlan 在 bpo-17839 [https://bugs.python.org/issue?@action=redirect&bpo=17839] 中贡献。)
新增的函数 a85encode()
, a85decode()
, b85encode()
以及 b85decode()
分别提供针对 Ascii85
以及 git/mercurial Base85
格式的二进制数据进行编码和解码的能力。 a85
函数具有可被用于使其与 Ascii85
编码格式的变种,包括 Adobe 变种相互兼容的选项。 (由 Martin Morrison, Mercurial 项目, Serhiy Storchaka 和 Antoine Pitrou 在 bpo-17618 [https://bugs.python.org/issue?@action=redirect&bpo=17618] 中贡献。)
collections
现在 ChainMap.new_child()
方法接受一个 m 参数用于指定要向链结构中添加的子映射表。 这允许将现有的映射和/或自定义映射类型用于子映射表。 (由 Vinay Sajip 在 bpo-16613 [https://bugs.python.org/issue?@action=redirect&bpo=16613] 中贡献。)
colorsys
用于 RGB —- YIQ 转换系数的数码位数已被扩展以使其与 FCC NTSC 版本匹配。 结果中的变化应当少于 1% 并可与在其他地方找到的结果更好地匹配。 (由 Brian Landers 和 Serhiy Storchaka 在 bpo-14323 [https://bugs.python.org/issue?@action=redirect&bpo=14323] 中贡献。)
contextlib
新增的 contextlib.suppress
上下文管理器可以帮助澄清故意抑制来自单条语句的异常的代码的意图。 (由 Raymond Hettinger 在 bpo-15806 [https://bugs.python.org/issue?@action=redirect&bpo=15806] 和 Zero Piraeus 在 bpo-19266 [https://bugs.python.org/issue?@action=redirect&bpo=19266] 中贡献。)
新增的 contextlib.redirect_stdout()
上下文管理器使得工具脚本能更容易地处理将输出写入 sys.stdout
并且不提供任何重定向选项的不灵活 API。 使用该上下文管理器,可以将 sys.stdout
的输出重定向到任何其他流,或者配合使用 io.StringIO
来重定向到字符串。 后一种方式有时会特别有用,例如写入函数的输出来实现 命令行接口。 由于它会影响 sys.stdout
的全局状态因此只推荐用于工具脚本。 (由 Raymond Hettinger 在 bpo-15805 [https://bugs.python.org/issue?@action=redirect&bpo=15805] 中贡献。)
contextlib
文档也已获得更新以包括有关仅单用、可重用与可重入上下文管理器之间的区别的 讨论。
dbm
现在 dbm.open()
对象已支持上下文管理器协议。 当在 with
语句中使用时,数据库对象的 close
方法将在代码块结束时被自动调用。 (由 Claudiu Popa 和 Nick Coghlan 在 bpo-19282 [https://bugs.python.org/issue?@action=redirect&bpo=19282] 中贡献。)
dis
现在 show_code()
, dis()
, distb()
和 disassemble()
等函数可接受仅限关键字参数 file 来控制其输出的写入目标。
现在 dis
模块是围绕 Instruction
类来构建的,该类以面向对象的访问方式提供对于每个单独字节码操作的细节。
新增的方法 get_instructions()
提供了一个为给定 Python 代码段产生 Instruction 流的迭代器。 这使得现在可以编写以不同于由 dis
模块本身所提供的方式检查和操纵字节码对象的程序。 例如:
- >>> import dis
- >>> for instr in dis.get_instructions(lambda x: x + 1):
- ... print(instr.opname)
- LOAD_FAST
- LOAD_CONST
- BINARY_ADD
- RETURN_VALUE
dis
模块中的各种显示工具已被重新编写以使用这些新组件。
此外,新增的对应用程序友好的类 Bytecode
提供了一个面向对象的 API 用于以人类可读的形式检查字节码并对指令进行迭代。 Bytecode
构造器接受与 get_instruction()
相同的参数(外加一个可选的 current_offset 参数),其结果对象可被迭代以产生 Instruction
对象。 但它还有一个 dis
方法,相当于在构造器参数上调用 dis
,但是返回一个多行字符串:
- >>> bytecode = dis.Bytecode(lambda x: x + 1, current_offset=3)
- >>> for instr in bytecode:
- ... print('{} ({})'.format(instr.opname, instr.opcode))
- LOAD_FAST (124)
- LOAD_CONST (100)
- BINARY_ADD (23)
- RETURN_VALUE (83)
- >>> bytecode.dis().splitlines()
- [' 1 0 LOAD_FAST 0 (x)',
- ' --> 3 LOAD_CONST 1 (1)',
- ' 6 BINARY_ADD',
- ' 7 RETURN_VALUE']
Bytecode
还有一个类方法 from_traceback()
,它提供了操纵回溯对象的能力(也就是说,print(Bytecode.from_traceback(tb).dis())
等价于 distb(tb)
。)
(由 Nick Coghlan, Ryan Kelly 和 Thomas Kluyver 在 bpo-11816 [https://bugs.python.org/issue?@action=redirect&bpo=11816] 并由 Claudiu Popa 在 bpo-17916 [https://bugs.python.org/issue?@action=redirect&bpo=17916] 中贡献。)
新增的函数 stack_effect()
可在给定操作码和参数的 Python 栈上计算其效果,相关信息是无法以其他方式获得的。 (由 Larry Hastings 在 bpo-19722 [https://bugs.python.org/issue?@action=redirect&bpo=19722] 中贡献。)
doctest
新增的 选项旗标 FAIL_FAST
将在检测到首次失败时暂停测试运行。 (由 R. David Murray 和 Daniel Urban 在 bpo-16522 [https://bugs.python.org/issue?@action=redirect&bpo=16522] 中贡献。)
现在 doctest
的命令行接口使用 argparse
,并新增了两个选项 -o
和 -f
。 -o
允许在命令行中指定 doctest 选项,而 -f
是 -o FAIL_FAST
的简写形式(与 unittest
CLI 所支持的类似选项相对应)。 (由 R. David Murray 在 bpo-11390 [https://bugs.python.org/issue?@action=redirect&bpo=11390] 中贡献。)
现在 doctest
会在扩展模块的 __doc__
字符串中查找文档测试。 (由 Zachary Ware 在 bpo-3158 [https://bugs.python.org/issue?@action=redirect&bpo=3158] 中贡献。)
现在 as_string()
接受一个 policy 参数用于在生成其字符串表示形式时重写默认的消息策略。 这意味着 as_string
现在可以在更多情况下被使用,而不必创建和使用 generator
来将已格式化的形参传递给其 flatten
方法。 (由 R. David Murray 在 bpo-18600 [https://bugs.python.org/issue?@action=redirect&bpo=18600] 中贡献。)
新增方法 as_bytes()
用于产生消息的与 as_string
所产生的字符串表示形式类似的字节串表示形式。 它不接受 maxheaderlen 参数,但接受 unixfrom 和 policy 参数。 Message
的 __bytes__()
方法将调用它,这意味着现在 bytes(mymsg)
将产生直观的结果:一个包含完整已格式化消息的字节串对象。 (由 R. David Murray 在 bpo-18600 [https://bugs.python.org/issue?@action=redirect&bpo=18600] 中贡献。)
现在 Message.set_param()
消息接受一个 replace 关键字参数。 当指定该参数时,关联的标头将被更新而不会修改其在标头列表中的位置。 为了保持向下兼容,该参数默认值为 False
。 (由 R. David Murray 在 bpo-18891 [https://bugs.python.org/issue?@action=redirect&bpo=18891] 中贡献。)
新增了一对 Message
的子类 (EmailMessage
和 MIMEPart
),以及新的子模块 contentmanager
和新的 policy
属性 content_manager
。 所有文档目前都在新模块中,它是作为 email 的新 provisional API 的一部分添加的。 这些类提供了多个使从内容提取邮件消息和插入内容到消息更容易的新方法。 相关细节,请参阅 contentmanager
文档和 email: 示例。 这些 API 的加入完成了作为 email6 项目计划组成部分的大部分工作。 目前的暂定 API 计划在 Python 3.5 最终确定 (可能在错误处理方面再增加少量内容)。 (由 R. David Murray 在 bpo-18891 [https://bugs.python.org/issue?@action=redirect&bpo=18891] 中贡献。)
filecmp
新增的 clear_cache()
函数提供了清除 filecmp
比较缓存的功能,它使用 os.stat()
信息来确定文件自上次比较后是否发生了更改。 例如,如果文件被修改和重新检查的时间短于特定文件系统文件修改时间的精度就可使用这一功能。 (由 Mark Levitt 在 bpo-18149 [https://bugs.python.org/issue?@action=redirect&bpo=18149] 中贡献。)
新增的模块属性 DEFAULT_IGNORES
提供了作为 dircmp()
函数的 ignore 形参默认值的目录列表。 (由 Eli Bendersky 在 bpo-15442 [https://bugs.python.org/issue?@action=redirect&bpo=15442] 中贡献。)
functools
新增的 partialmethod()
描述器提供了对描述器的部分参数应用,就像 partial()
为普通可调用对象提供的一样。 新的描述器还可以让任意可调用对象 (包括 partial()
实例)在包括在类定义中时表现得像普通的实例方法一样。 (由 Alon Horev 和 Nick Coghlan 在 bpo-4331 [https://bugs.python.org/issue?@action=redirect&bpo=4331] 中贡献。)
新增的 singledispatch()
装饰器为 Python 标准库带来了对单分派泛型函数的支持。 面向对象编程侧重于将对一组共同数据的多种操作组合到一个类中,而泛型函数则侧重于将一种操作的多个实现组合在一起使其能够处理 不同 种类的数据。
参见
- PEP 443 [https://peps.python.org/pep-0443/] — 单分派泛型函数
- PEP 由 Łukasz Langa 撰写并实现。
现在 total_ordering()
支持从下层的比较函数返回 NotImplemented
作为返回值。 (由 Katie Miller 在 bpo-10042 [https://bugs.python.org/issue?@action=redirect&bpo=10042] 中贡献。)
现在标准库中增加了 partial()
函数的纯 Python 版本;在 CPython 中它会被 C 加速版本覆盖,但它以供其他实现来使用。 (由 Brian Thorne 在 bpo-12428 [https://bugs.python.org/issue?@action=redirect&bpo=12428] 中贡献。)
gc
新增的函数 get_stats()
可返回由三个单独生成字典组成的列表,每个字典均包含自解释器启动以来收集的统计信息。 (由 Antoine Pitrou 在 bpo-16351 [https://bugs.python.org/issue?@action=redirect&bpo=16351] 中贡献。)
glob
新增函数 escape()
提供了为文件名中的特殊字符进行转义的方式以使它们不会成为 glob 扩展的组成部分而是按字面值来匹配。 (由 Serhiy Storchaka 在 bpo-8402 [https://bugs.python.org/issue?@action=redirect&bpo=8402] 中贡献。)
hashlib
新增的 hashlib.pbkdf2_hmac()
函数提供了 PKCS#5 基于口令的密钥派生函数 2 [https://en.wikipedia.org/wiki/PBKDF2]。 (由 Christian Heimes 在 bpo-18582 [https://bugs.python.org/issue?@action=redirect&bpo=18582] 中贡献。)
现在 hashlib
哈希对象的 name
属性已成为受正式支持的接口。 它一直存在于 CPython 的 hashlib
中(尽管它没有返回所有受支持的哈希算法的小写名称),但它不是一个公开的接口因此其他一些 Python 实现以前并不支持它。 (由 Jason R. Coombs 在 bpo-18532 [https://bugs.python.org/issue?@action=redirect&bpo=18532] 中提供。)
hmac
现在 hmac
可接受 bytearray
和 bytes
作为传给 new()
函数的 key 参数,而传给 new()
函数和 update()
方法的 msg 形参现在可接受 hashlib
模块所支持的任何类型。 (由 Jonas Borgström 的 bpo-18240 [https://bugs.python.org/issue?@action=redirect&bpo=18240] 中贡献。)
传给 hmac.new()
函数的 digestmod 参数现在可以是 hashlib
能识别的任何哈希摘要名称。 此外,当前将 digestmod 默认值设为 MD5
的行为已被弃用:在未来的 Python 版本中将没有默认值。 (由 Christian Heimes 在 bpo-17276 [https://bugs.python.org/issue?@action=redirect&bpo=17276] 中贡献。)
由于增加了 block_size
和 name
属性 (以及 digest_size
属性的正式文档),hmac
模块现在已完全符合 PEP 247 [https://peps.python.org/pep-0247/] API。 (由 Christian Heimes 在 bpo-18775 [https://bugs.python.org/issue?@action=redirect&bpo=18775] 中贡献。)
html
新增的函数 unescape()
用于将 HTML5 字符引用转换为相应的 Unicode 字符。 (由 Ezio Melotti 在 bpo-2927 [https://bugs.python.org/issue?@action=redirect&bpo=2927] 中贡献。).) HTMLParser
接受新的关键字参数 convert_charrefs,当其为 True
时,会自动转换所有字符引用。 为了保持向下兼容,其值默认为 False
,但在未来的 Python 版本中将改为 True
,因此建议你显式地设置它并更新代码以使用这个新特性。 (由 Ezio Melotti 在 bpo-13633 [https://bugs.python.org/issue?@action=redirect&bpo=13633] 中贡献。)
现在 HTMLParser
的 strict 参数已被弃用。 (由 Ezio Melotti 在 bpo-15114 [https://bugs.python.org/issue?@action=redirect&bpo=15114] 中贡献。)
http
现在 send_error()
接受可选的附加形参 explain 用于提供扩展的错误描述,覆盖可能存在的硬编码的默认值。 这个扩展的描述将使用 error_message_format
进行格式化并作为错误响应体发送。 (由 Karl Cow 在 bpo-12921 [https://bugs.python.org/issue?@action=redirect&bpo=12921] 中贡献。)
现在 http.server
命令行界面 增加了一个 -b/--bind
选项用于让服务器在指定的地址上进行监听。 (由 Malte Swart 在 bpo-17764 [https://bugs.python.org/issue?@action=redirect&bpo=17764] 中贡献。)
idlelib 与 IDLE
由于 idlelib 实现了 IDLE 命令行界面和编辑器且不应被其他程序导入,它将随每个发布版获得改进。 请参阅 Lib/idlelib/NEWS.txt
查看 3.3.0 以来的累积变化列表,以及未来 3.4.x 发布版即将发生的变化。 此文件也可通过 IDLE Help ‣ About IDLE 对话框来查看。
importlib
InspectLoader
ABC 定义了一个新方法 source_to_code()
,它接受源数据和一个路径并返回一个代码对象。 其默认实现等价于 compile(data, path, 'exec', dont_inherit=True)
。 (由 Eric Snow 和 Brett Cannon 在 bpo-15627 [https://bugs.python.org/issue?@action=redirect&bpo=15627] 中贡献。)
现在 InspectLoader
也具有 get_code()
方法的默认实现。 不过,出于性能原因通常需要重写默认实现。 (由 Brett Cannon 在 bpo-18072 [https://bugs.python.org/issue?@action=redirect&bpo=18072] 中贡献。)
由于 imp
模块被弃用 reload()
函数已从 imp
移至 importlib
。 (由 Berker Peksag 在 bpo-18193 [https://bugs.python.org/issue?@action=redirect&bpo=18193] 中贡献。)
importlib.util
now has a MAGIC_NUMBER
attribute providing access to the bytecode version number. This replaces the get_magic()
function in the deprecated imp
module. (Contributed by Brett Cannon in bpo-18192 [https://bugs.python.org/issue?@action=redirect&bpo=18192].) 新增的 importlib.util
函数 cache_from_source()
和 source_from_cache()
替换了已弃用的 imp
模块中的同名函数。 (由 Brett Cannon 在 bpo-18194 [https://bugs.python.org/issue?@action=redirect&bpo=18194] 中贡献。)
现在 importlib
将以符合 InspectLoader
ABC 的方式初始设置 NamespaceLoader
,这意味着 runpy
现在可以与命名空间包一起使用。 (由 Brett Cannon 在 bpo-18058 [https://bugs.python.org/issue?@action=redirect&bpo=18058] 中贡献。)和
python -m
importlib.util
中新增的函数 decode_source()
可使用通用换行处理方式从字节数据中解码源代码。 这适用于实现 InspectLoader.get_source()
方法。
现在 importlib.machinery.ExtensionFileLoader
增加了 get_filename()
方法。 此方法在最初的实现中意外缺失。 (由 Eric Snow 在 bpo-19152 [https://bugs.python.org/issue?@action=redirect&bpo=19152] 中贡献。)
inspect
现在 inspect
模块提供了一个基本的 命令行界面 用于快速显示模块、类和函数的源代码以及其他信息。 (由 Claudiu Popa 和 Nick Coghlan 在 bpo-18626 [https://bugs.python.org/issue?@action=redirect&bpo=18626] 中贡献。)
unwrap()
用于方便地解开由 functools.wraps()
(以及任何在包装器函数上设置 __wrapped__
属性的 API) 创建的包装器函数链。 (由 Daniel Urban, Aaron Iles 和 Nick Coghlan 在 bpo-13266 [https://bugs.python.org/issue?@action=redirect&bpo=13266] 中贡献。)
作为新的 enum
模块实现的一部分,现在 inspect
模块通过元类为自定义 __dir__
方法和动态类属性提供了更好的支持。 (由 Ethan Furman 在 bpo-18929 [https://bugs.python.org/issue?@action=redirect&bpo=18929] 和 bpo-19030 [https://bugs.python.org/issue?@action=redirect&bpo=19030] 中贡献。)
现在 getfullargspec()
和 getargspec()
将使用 signature()
API。 这允许它们支持更多种类的可调用对象,包括具有 __signature__
属性的、具有通过 argument clinic 提供元数据的、functools.partial()
对象等等。 请注意,不同于 signature()
,这些函数仍然会忽略 __wrapped__
属性,并会报告绑定方法已绑定的第一个参数,所以如果想要这些特性的话你仍然需要更新你的代码以直接使用 signature()
。 (由 Yury Selivanov 在 bpo-17481 [https://bugs.python.org/issue?@action=redirect&bpo=17481] 中贡献。)
现在 signature()
支持 CPython 函数的鸭子类型,它增加了对使用 Cython 编译的函数的支持。 (由 Stefan Behnel 和 Yury Selivanov 在 bpo-17159 [https://bugs.python.org/issue?@action=redirect&bpo=17159] 中贡献。)
ipaddress
ipaddress
已在 Python 3.3 中作为 provisional API 被添加到标准库。 随着 Python 3.4 的发布,此限定已被移除:现在 ipaddress
属于稳定 API,由常规的标准库需求所覆盖以维护向下兼容性。
如果一个地址是全局可路由的则新增的 is_global
属性将为 True
。 (由 Peter Moody 在 bpo-17400 [https://bugs.python.org/issue?@action=redirect&bpo=17400] 中贡献。)
logging
TimedRotatingFileHandler
新增的 atTime 形参可被用于指定每日要执行日志文件轮转的时间。 (由 Ronald Oussoren 在 bpo-9556 [https://bugs.python.org/issue?@action=redirect&bpo=9556] 中贡献。)
现在 SocketHandler
和 DatagramHandler
已支持 Unix 域套接字 (通过将 port 设为 None
)。 (由 Vinay Sajip 在 commit ce46195b56a9 中贡献。)
现在 fileConfig()
接受一个 configparser.RawConfigParser
子类实例作为 fname 形参。 这有助于在日志配置只是整体应用程序配置的一部分,或者在将配置传递给 fileConfig()
之前对其进行了修改时使用配置文件。 (由 Vinay Sajip 在 bpo-16110 [https://bugs.python.org/issue?@action=redirect&bpo=16110] 中贡献。)
现在通过 logging.config.listen()
函数从套接字接收的日志配置数据可以在处理前以将验证函数作为参数提供给新的 verify 关键字参数 的方式执行验证。 (由 Vinay Sajip 在 bpo-15452 [https://bugs.python.org/issue?@action=redirect&bpo=15452] 中贡献。)
marshal
默认的 marshal
版本已被提升至 3。 新版本的代码实现恢复了 Python2 行为即只记录内联字符串的一份副本并在反序列化时保留内联状态,并将此“一份副本”功能扩展到任何对象类型(包括处理递归引用)。 这既减少了 .pyc
文件的大小也减少了模块从 .pyc
(或.pyo
) 文件加载时占用的内存量。 (由 Kristján Valur Jónsson 在 bpo-16475 [https://bugs.python.org/issue?@action=redirect&bpo=16475] 中贡献,并由 Antoine Pitrou 在 bpo-19219 [https://bugs.python.org/issue?@action=redirect&bpo=19219] 中提供进一步的加速。)
mmap
现在 mmap 对象将是 可弱引用的。 (由 Valerie Lambert 在 bpo-4885 [https://bugs.python.org/issue?@action=redirect&bpo=4885] 中贡献。)
multiprocessing
在 Unix 上新增了两个 启动方法 spawn
和 forkserver
可使用 multiprocessing
来启动进程。 这两个方法使得进程和线程的混合更为健壮,并且 spawn
方法可以匹配 multiprocessing 在 Windows 上一直使用的语法。 新增的函数 get_all_start_methods()
可报告平台上可用的所有启动方法,get_start_method()
可报告当前的启动方法,而 set_start_method()
可设置启动方法。 (由 Richard Oudkerk 在 bpo-8713 [https://bugs.python.org/issue?@action=redirect&bpo=8713] 中贡献。)
现在 multiprocessing
还具有 上下文
的概念,它决定了子进程的创建方式。 新增的函数 get_context()
可返回一个使用指定启动方法的上下文。 它具有与 multiprocessing
模块本身一致的 API,因此你可以使用它来创建 Pool
和其他在上下文中执行操作的对象。 这允许一个框架和某个应用程序或相同应用程序的不同部分使用多进程而不会彼此干扰。 (由 Richard Oudkerk 在 bpo-18999 [https://bugs.python.org/issue?@action=redirect&bpo=18999] 中贡献。)
除非是在使用旧的 fork 启动方法,子进程将不再从其父进程继承不需要的句柄/文件描述符 (bpo-8713 [https://bugs.python.org/issue?@action=redirect&bpo=8713] 的一部分)。
现在当使用 spawn
或 forkserver
启动方法时 multiprocessing
依赖于 runpy
(它实现了 -m
开关) 在子进程中正确地初始化 __main__
。 这解决了一些合并多进程操作中,-m
命令行开关和显式相对导入可能在子进程中导致失败的边缘场景问题。 (由 Nick Coghlan 在 bpo-19946 [https://bugs.python.org/issue?@action=redirect&bpo=19946] 中贡献。)
operator
新增的函数 length_hint()
提供了应当如何使用 __length_hint__()
特殊方法的规范实现,作为该语言特性的 PEP 424 [https://peps.python.org/pep-0424/] 正式规范说明的一部分。 (由 Armin Ronacher 在 bpo-16148 [https://bugs.python.org/issue?@action=redirect&bpo=16148] 中贡献。)
现在提供了一个纯 Python 版本的 operator
模块,可用于参考并由 Python 的其他实现使用。 (由 Zachary Ware 在 bpo-16694 [https://bugs.python.org/issue?@action=redirect&bpo=16694] 中贡献。)
os
新增一些函数用于获取和设置文件描述符或 Windows 句柄的 可继承旗标 (os.get_inheritable()
, os.set_inheritable()
) 或 (os.get_handle_inheritable()
, os.set_handle_inheritable()
)。
新增函数 cpu_count()
可报告 Python 运行所在平台上可用 CPU 的数量 (如果无法确定数量则为 None
)。 现在 multiprocessing.cpu_count()
函数是根据此函数实现的。 (由 Trent Nelson, Yogesh Chaudhari, Victor Stinner 和 Charles-François Natali 在 bpo-17914 [https://bugs.python.org/issue?@action=redirect&bpo=17914] 中贡献。)
现在 os.path.samestat()
将在 Windows 平台上可用(并且现在 os.path.samefile()
实现可在 Unix 和 Windows 间共享)。 (由 Brian Curtin 在 bpo-11939 [https://bugs.python.org/issue?@action=redirect&bpo=11939] 中贡献。)
现在 os.path.ismount()
可识别 Windows 中在驱动器根目录下加载的卷。 (由 Tim Golden 在 bpo-9035 [https://bugs.python.org/issue?@action=redirect&bpo=9035] 中贡献。)
os.open()
在受支持的平台上提供了两个新旗标 O_PATH
(未打开的文件描述符) 和 O_TMPFILE
(未命名的临时文件;因为 3.4.0 发布版仅在具有 uapi 标头的内核版本 3.11 或更新的 Linux 系统上可用)。 (分别由 Christian Heimes 在 bpo-18673 [https://bugs.python.org/issue?@action=redirect&bpo=18673] 中以及 Benjamin Peterson 贡献。)
pdb
pdb
已被增强以通过更有用的方式来处理生成器, yield
和 yield from
。 这在调试基于 asyncio
的程序时特别有帮助。 (由 Andrew Svetlov 和 Xavier de Gaye 在 bpo-16596 [https://bugs.python.org/issue?@action=redirect&bpo=16596] 中贡献。)
print
命令已从 pdb
中移除,恢复了从 pdb 命令行对 Python print()
函数的访问。 Python2 的 pdb
没有 print
命令;而是会在输入 print
时执行 print
语句。 在 Python3 中 print
被错误地设为 pdb p
命令的别名。 然而,p
会打印其参数的 repr
,而不是像 Python2 print
命令那样打印其参数的 str
。 更糟糕的是,Python3 pdb print
命令会覆盖 Python3 print
函数,导致其在 pdb
提示符下无法被访问。 (由 Connor Osborn 在 bpo-18764 [https://bugs.python.org/issue?@action=redirect&bpo=18764] 中贡献。)
pickle
现在 pickle
支持(但默认不使用)新的 pickle 协议即协议 4。 这个新协议解决了在之前版本中存在的多个问题,例如嵌套类、超长字符串和容器、以及 __new__()
方法接受仅限关键字参数的类的序列化。 它还提供了一些效率上的改进。
参见
- PEP 3154 [https://peps.python.org/pep-3154/] — pickle 协议 4
- PEP 由 Antoine Pitrou 撰写,并由 Alexandre Vassalotti 实现
plistlib
现在 plistlib
个具有与 stdlib 序列化协议标准模式类似的 API,使用新的 load()
, dump()
, loads()
和 dumps()
函数。 (旧 API 现已被弃用。) 除了已受支持的 XML plist 格式 (FMT_XML
),现在它还支持二进制 plist 格式 (FMT_BINARY
)。 (由 Ronald Oussoren 等人在 bpo-14455 [https://bugs.python.org/issue?@action=redirect&bpo=14455] 中贡献。)