Python 3.7 有什么新变化
- 编者:
- Elvis Pranskevichus <elvis@magic.io>
本文解释了 Python 3.7 相比 3.6 的新增特性。Python 3.7 于 2018 年 6 月 27 日发布。完整的详情可参阅 更新日志。
摘要 - 发布重点
新的语法特性:
- PEP 563,类型标注延迟求值。
向后不兼容的语法更改:
新的库模块:
新的内置特性:
- PEP 553, 新的
breakpoint()
函数。
对 Python 数据模型的改进:
PEP 562, 自定义可访问的模块属性。
PEP 560, typing模块和泛型类型的核心支持。
dict 对象会保持插入时的顺序这个特性 正式宣布 [https://mail.python.org/pipermail/python-dev/2017-December/151283.html] 成为 Python 语言官方规范的一部分。
标准库中的重大改进:
CPython 实现的改进:
避免使用 ASCII 作为默认的文本编码:
PEP 552,确定性的 .pyc 文件
PEP 565,改进的
DeprecationWarning
处理
C API 的改进:
- PEP 539,用于线程本地存储的新 C API
文档的改进:
PEP 545, Python 文档翻译
新的文档翻译:Japanese [https://docs.python.org/ja/],[French](https://docs.python.org/fr/) [https://docs.python.org/fr/] 和 Korean [https://docs.python.org/ko/]。
此版本在诸多方面有显著的性能改进。性能优化 章节详细列出了它们。
和之前的 Python 版本存在兼容性的更改列表,请参阅 移植到 Python 3.7 章节。
新的特性
PEP 563:延迟的标注求值
随着 PEP 3107 [https://peps.python.org/pep-3107/] 加入标注功能并在 PEP 526 [https://peps.python.org/pep-0526/] 进一步细化,Python 中类型提示的出现揭示了两个明显的可用性问题:
标注只能使用在当前作用域中已经存在的名称,也就是说,它们不支持任何形式的前向引用;而且——
标注源码对 Python 程序的启动时间有不利的影响。
这两个问题都可以通过延迟标注求值来解决。在定义标注的时候,编译器并不会编译执行相应表达式的代码,而是保存与相应表达式的 AST 等价的字符串形式。如果有需要,标注可以在运行时使用 typing.get_type_hints()
进行解析。在不需要这种解析的通常情况下,标注的存储成本更低(因为解析器只需处理较短的字符串)且启动时间更短。
在可用性方面,标注现在支持向前引用,以使以下句法有效:
- class C:
- @classmethod
- def from_string(cls, source: str) -> C:
- ...
- def validate_b(self, obj: B) -> bool:
- ...
- class B:
- ...
由于此修改会破坏兼容性,在 Python 3.7 中此种新的行为需要在每个模块层级上使用 __future__
导入来启用:
- from __future__ import annotations
它将在 Python 3.10 中成为默认行为。
参见
- PEP 563 [https://peps.python.org/pep-0563/] — 延迟的标注求值
- PEP 由 Łukasz Langa 撰写并实现。
PEP 538: 传统 C 区域强制转换
Python 3 系列有一个持续的挑战就是为处理 7 比特位 ASCII 文本的假定编码确定合理的默认策略,目前的设定是在非 Windows 平台上使用默认的 C 或 POSIX 区域设置。
PEP 538 [https://peps.python.org/pep-0538/] 更新了默认的解释器命令行接口,以自动将上述区域强制转换为可用的基于 UTF-8 的区域,具体描述可参见有关新增环境变量 PYTHONCOERCECLOCALE
的文档。 以这种方式自动设置 LC_CTYPE
意味着核心解释器和能感知区域的 C 扩展 (例如 readline
) 都将会假定 UTF-8 已被用作默认的文本编码,而不再是 ASCII。
PEP 11 [https://peps.python.org/pep-0011/] 中的平台支持定义也已被更新以限制完整文本处理支持适当配置的基于非 ASCII 的语言区域。
作为此更改的一部分,当使用任何已定义的强制转换目标区域时 (目前为 C.UTF-8
, C.utf8
和 UTF-8
) stdin
和 stdout
默认的处理器现在将为 surrogateescape
(而不是 strict
)。 而无论是什么区域,stderr
默认的处理器仍为 backslashreplace
。
默认情况下区域强制转换会静默进行,但为了辅助调试潜在的区域相关集成问题,可以通过设置 PYTHONCOERCECLOCALE=warn
来请求显式地启用警告信息(直接在 stderr
上发出)。 此设置还会使得 Python 运行时在核心解释器初始化时如果传统 C 区域仍然处于激活状态时发出警告。
虽然 PEP 538 [https://peps.python.org/pep-0538/] 的区域强制转换的好处在于它还会同时影响扩展模块 (例如 GNU readline
) 以及子进程 (包括运行非 Python 应用和旧版本 Python 的子进程),但它也存在需要所运行系统必须存在适合的目标区域的缺点。 为了更好地处理没有可用适合的目标区域的情况 (例如在 RHEL/CentOS 7 上就会出现此情况),Python 3.7 还实现了 PEP 540: 强制 UTF-8 运行时模式。
参见
- PEP 538 [https://peps.python.org/pep-0538/] — 强制转换传统 C 区域到基于 UTF-8 的区域
- PEP 由 Nick Coghlan 撰写并实现。
PEP 540: 强制 UTF-8 运行时模式
新的 -X
utf8
命令行选项和 PYTHONUTF8
环境变量可被用来启用 Python UTF-8 模式。
当处于 UTF-8 模式时,CPython 会忽略区域设置,并默认使用 UTF-8 编码。 用于 sys.stdin
和 sys.stdout
流的错误处理器将设置为 surrogateescape
。
强制 UTF-8 模式可被用来在嵌入的 Python 解释器中改变文本处理行为,而不会改变嵌入方应用的区域设置。
PEP 540 [https://peps.python.org/pep-0540/] 的 UTF-8 模式的好处是不必关心运行所在系统中有哪些可用区域即可工作,但它也存在对扩展模块 (例如 GNU readline
)、运行非 Python 应用的子进程以及运行旧版本 Python 的子进程不起作用的缺点。 为了减小与这些组件通信时破坏文本数据的风险,Python 3.7 还实现了 PEP 540: 强制 UTF-8 运行时模式)。
UTF-8 模式在语言区域为 C
或 POSIX
并且 PEP 538 [https://peps.python.org/pep-0538/] 区域强制转换特性无法将其修改为某种基于 UTF-8 的替代项时会被默认启用(无论修改失败是由于设置了 PYTHONCOERCECLOCALE=0
, LC_ALL
还是由于缺少适合的目标区域)。
参见
- PEP 540 [https://peps.python.org/pep-0540/] — 增加了新的 UTF-8 模式
- PEP 由 Victor Stinner 撰写并实现
PEP 553: 内置的 breakpoint()
Python 3.7 包含了新的内置 breakpoint()
函数,作为一种简单方便地进入 Python 调试器的方式。
内置 breakpoint()
会调用 sys.breakpointhook()
。 在默认情况下后者会导入 pdb
然后再调用 pdb.set_trace()
,但是通过将 sys.breakpointhook()
绑定到你选定的函数,breakpoint()
可以进入任何调试器。 此外,环境变量 PYTHONBREAKPOINT
可被设置为你选定的调试器的可调用对象。 设置 PYTHONBREAKPOINT=0
会完全禁用内置 breakpoint()
。
参见
- PEP 553 [https://peps.python.org/pep-0553/] — 内置的 breakpoint()
- PEP 由 Barry Warsaw 撰写并实现
PEP 539: 用于线程局部存储的新 C API
虽然 Python 提供了用于线程存储支持的 C API;但原有的 线程局部存储 (TLS) API 已使用 int 来表示所有平台上的 TLS 密钥。 对于官方支持的平台而言这通常不是问题,但这即不符合 POSIX 标准,也不具备任何实际意义上的可移植性。
PEP 539 [https://peps.python.org/pep-0539/] 通过向 CPython 提供一个取代 CPython 解释器内部的现有 TLS API 的使用的新的 线程专属存储 (TSS) API 来改变这一点,同时弃用了现有的 API。 TSS API 使用一种新类型 Py_tss_t
而非 int 来表示 TSS 密钥 — 这是一种具体定义依赖于下层 TLS 实现的不透明类型。 因此,这将允许在以无法安全地转换为 int 的方式定义原生 TLS 密钥的平台上构建 CPython。
请注意在 TLS 密钥定义方式使其无法被安全地转换为 int 的平台上,现有 TLS API 中的全部函数将无法执行并会立即返回失败信息。 这样可以清楚地表明原有 API 在无法可选使用的平台上不受支持,并且也不准备添加此种支持。
参见
- PEP 539 [https://peps.python.org/pep-0539/] — 在 CPython 中用于线程局部存储的新 C-API
- PEP 由 Erik M. Bray 撰写;由 Masayuki Yamamoto 实现。
PEP 562: 定制对模块属性的访问
Python 3.7 允许在模块上定义 __getattr__()
并且当以其他方式找不到某个模块属性时将会调用它。 在模块上定义 __dir__()
现在也是允许的。
一个典型的可能有用的例子是已弃用模块属性和惰性加载。
参见
- PEP 562 [https://peps.python.org/pep-0562/] — 模块的
__getattr__
和__dir__
- PEP 由 Ivan Levkivskyi 撰写并实现
PEP 564: 具有纳秒级精度的新时间函数
现代系统的时钟精度可以超过由 time.time()
函数及其变化形式所返回的浮点数的有限精度。 为了避免精度损失, PEP 564 [https://peps.python.org/pep-0564/] 在 time
模块中增加了原有计时器函数的六个新“纳秒版”变化形式:
这些新函数会以整数值的形式返回纳秒数。
测量结果 [https://peps.python.org/pep-0564/#annex-clocks-resolution-in-python] 显示在 Linux 和 Windows 上 time.time_ns()
的精度相比 time.time()
大约高出 3 倍。
参见
- PEP 564 [https://peps.python.org/pep-0564/] — 增加具有纳秒级精度的新时间函数
- PEP 由 Victor Stinner 撰写并实现
PEP 565: 在 __main__
中显示 DeprecationWarning
DeprecationWarning
的默认处理方式已经被更改,这此警告默认只显示一次,仅有当直接在 __main__
模块中运行的代码触发它们时才会再次显示。 因此,单文件脚本开发者以及 Python 交互模式使用者应该会再次开始看到针对他们所使用 API 的已弃用警告,但被导入应用、库和框架模块所触发的已弃用警告默认将继续隐藏。
作为此项更改的结果,标准库现在允许开发者在三种不同的已弃用警告行为之间进行选择:
FutureWarning
: 默认情况下总是会显示,建议用于应用程序最终用户应该看到的警告信息(例如对于已弃用的应用程序配置的设置选项)。DeprecationWarning
: 默认情况下仅在__main__
中以及当运行测试时会显示,建议用于其他 Python 开发者应该看到的警告信息,提示版本升级可能导致行为改变或者错误。PendingDeprecationWarning
: 默认情况下仅在运行测试时会显示,可用于提示未来版本升级将会改变警告类别为DeprecationWarning
或FutureWarning
的情况。
在此之前 DeprecationWarning
和 PendingDeprecationWarning
都仅在运行测试时可见,这意味着主要编写单文件脚本或使用 Python 交互模式的开发者可能会因他们所用 API 突然出现的改变而感到惊讶。
参见
- PEP 565 [https://peps.python.org/pep-0565/] — 在
__main__
中显示 DeprecationWarning - PEP 由 Nick Coghlan 撰写并实现
PEP 560: 对 typing
模块和泛型类型的核心支持
PEP 484 [https://peps.python.org/pep-0484/] 最初的设计方式使其不会向核心 CPython 解释器引入 任何 更改。 现在类型提示和 typing
模块已被社区广泛使用,因此这个限制已被取消。 这个 PEP 引入了两个特殊方法 __class_getitem__()
和 __mro_entries__
,这些方法现在被 typing
中的大多数类和特殊构造所使用。 结果就是与类型相关的各类操作的速度提升了 7 倍,泛型类型可以在没有元类冲突的情况下被使用,而 typing
模块中几个长期存在的错误也已被修正。
参见
- PEP 560 [https://peps.python.org/pep-0560/] — 对 typing 模块和泛型类型的核心支持
- PEP 由 Ivan Levkivskyi 撰写并实现
PEP 552: 基于哈希值的 .pyc 文件
传统上 Python 检查字节码缓存文件 (即 .pyc
文件) 是否最新的方式是通过对源码元数据 (最后更改的时间戳和大小)和生成缓存时保存在其文件头中的源码元数据进行比较。 这种检查方法虽然有效,但也存在缺点。 当文件系统的时间戳太粗糙时,Python 有可能错过源码更新,导致用户感到困惑。 此外,在缓存文件中存在时间戳对于 构建可再现 [https://reproducible-builds.org/] 并且基于内容的构建系统来说是有问题的。
PEP 552 [https://peps.python.org/pep-0552/] 扩展了 pyc 格式以允许使用源文件的哈希值而非源文件的时间戳来检查有效性。 这种 .pyc
文件就称为“基于哈希值的”。 默认情况下,Python 仍然使用基于时间戳的有效性检查,不会在运行时生成基于哈希值的 .pyc
文件。 基于哈希值的 .pyc
文件可以使用 py_compile
或 compileall
来生成。
基于哈希值的 .pyc
文件包含两种变体:已选定和未选定。 Python 会在运行时针对相应源码文件验证已选定基于哈希值的 .pyc
文件,但对未选定基于哈希值的 pyc 文件则不会这样做。 未选定基于哈希值的 .pyc
文件对于需要由 Python 外部的系统(例如构建系统)负责使 .pyc
文件保持最新的环境来说是一种有用的性能优化。
请参阅 已缓存字节码的失效 了解更多信息。
参见
- PEP 552 [https://peps.python.org/pep-0552/] — 确定性的 pyc 文件
- PEP 由 Benjamin Peterson 撰写并实现
PEP 545: Python 文档翻译
PEP 545 [https://peps.python.org/pep-0545/] 描述了创建和维护 Python 文档翻译的整个过程。
新增了三个新的翻译版本:
参见
- PEP 545 [https://peps.python.org/pep-0545/] — Python 文档翻译
- PEP 由 Julien Palard, Inada Naoki 和 Victor Stinner 撰写并实现。
Python 开发模式 (-X dev)
新的 -X
dev
命令行选项或新的 PYTHONDEVMODE
环境变量可被用来启用 Python 开发模式。 在开发模式下,Python 将执行额外的如果默认启用会导致开销过大的运行时检查。 请参阅 Python 开发模式 文档查看完整说明。
其他语言特性修改
await
表达式和包含async for
子句的推导式不允许在 格式化字符串字面值 的表达式中使用。 在 Python 3.7 中此限制已被取消。现在可以将超过 255 个参数传递给一个函数,而现在一个函数也可以拥有超过 255 个形参。 (由 Serhiy Storchaka 在 bpo-12844 [https://bugs.python.org/issue?@action=redirect&bpo=12844] 和 bpo-18896 [https://bugs.python.org/issue?@action=redirect&bpo=18896] 中贡献。)
现在
bytes.fromhex()
和bytearray.fromhex()
会忽略所有 ASCII 空白符,而非仅是空格符. (由 Robert Xiao 在 bpo-28927 [https://bugs.python.org/issue?@action=redirect&bpo=28927] 中贡献。)str
,bytes
和bytearray
获得了对新isascii()
方法的支持,该方法可被用来测试是个字符串或字节串是否仅包含 ASCII 字符。 (由 INADA Naoki 在 bpo-32677 [https://bugs.python.org/issue?@action=redirect&bpo=32677] 中贡献。)现在当
from … import …
失败时ImportError
会显示模块名称和模块__file__
路径。 (由 Matthias Bussonnier 在 bpo-29546 [https://bugs.python.org/issue?@action=redirect&bpo=29546] 中贡献。)现在已支持涉及将子模块绑定到一个名称的绝对导入的循环导入。 (由 Serhiy Storchaka 在 bpo-30024 [https://bugs.python.org/issue?@action=redirect&bpo=30024] 中贡献。)
现在
object.__format__(x, '')
等价于str(x)
而非format(str(self), '')
。 (由 Serhiy Storchaka d bpo-28974 [https://bugs.python.org/issue?@action=redirect&bpo=28974] 中贡献。)为了更好地支持栈跟踪的动态创建,现在
types.TracebackType
可以从 Python 代码中被实例化,并且 回溯对象 的tb_next
属性现在是可写的。 (由 Nathaniel J. Smith 在 bpo-30579 [https://bugs.python.org/issue?@action=redirect&bpo=30579] 中贡献。)当使用
-m
开关时,现在sys.path[0]
会主动扩展为完整的起始目录路径,而不是保持为空目录(这将允许在发生导入时从 当前 工作目录导入) (由 Nick Coghlan 在 bpo-33053 [https://bugs.python.org/issue?@action=redirect&bpo=33053] 中贡献。)新的
-X
importtime
选项或PYTHONPROFILEIMPORTTIME
环境变量可被用来显示每次模块导入的时间。 (由 Inada Naoki 在 bpo-31415 [https://bugs.python.org/issue?@action=redirect&bpo=31415] 中贡献。)
新增模块
contextvars
新的 contextvars
模块和一组 新的 C API 引入了对 上下文变量 的支持。 上下文变量在概念上类似于线程局部变量。 与 TLS 不同,上下文变量能正确地支持异步代码。
asyncio
和 decimal
已得到更新以使用和支持开箱即用的上下文变量。 特别是激活的 decimal 上下文现在将存储在上下文变量中,它允许十进制运算在异步代码中使用正确的上下文。
参见
- PEP 567 [https://peps.python.org/pep-0567/] — 上下文变量
- PEP 由 Yury Selivanov 撰写并实现
dataclasses
新的 dataclass()
装饰器提供了一种声明 数据类 的方式。 数据类使用变量标注来描述其属性。 它的构造器和其他魔术方法例如 __repr__()
, __eq__()
以及 __hash__()
会自动地生成。
示例:
- @dataclass
- class Point:
- x: float
- y: float
- z: float = 0.0
p = Point(1.5, 2.5)
print(p) # produces "Point(x=1.5, y=2.5, z=0.0)"
参见
- PEP 557 [https://peps.python.org/pep-0557/] — 数据类
- PEP 由 Eric V. Smith 撰写并实现
importlib.resources
新的 importlib.resources
模块提供了一些新的 API 和一个新的 ABC 用于访问、打开和读取包内的 资源。 资源大致类似于包内的文件,但它们不一定是物理文件系统中实际的文件。 模块加载器可以提供一个 get_resource_reader()
函数,它会返回一个 importlib.abc.ResourceReader
实例来支持这个新 API。 内置的文件路径加载器和 zip 文件加载器都支持此特性。
由 Barry Warsaw 和 Brett Cannon 在 bpo-32248 [https://bugs.python.org/issue?@action=redirect&bpo=32248] 中贡献。
参见
importlib_resources [https://importlib-resources.readthedocs.io/en/latest/] — 用于较早版本 Python 的 PyPI 向下移植包。
改进的模块
argparse
新的 ArgumentParser.parse_intermixed_args()
方法允许混合选项与位置参数。 (由 paul.j3 在 bpo-14191 [https://bugs.python.org/issue?@action=redirect&bpo=14191] 中提供。)
asyncio
asyncio
模块获得了许多新的特性、可用性和 性能提升。 重要的改变包括:
新的 暂定
asyncio.run()
函数可被用于通过自动创建和销毁事件循环来基于同步代码运行协程。 (由 Yury Selivanov 在 bpo-32314 [https://bugs.python.org/issue?@action=redirect&bpo=32314] 中贡献。)asyncio 增加支持
contextvars
.loop.call_soon()
,loop.call_soon_threadsafe()
,loop.call_later()
,loop.call_at()
并且Future.add_done_callback()
具有新的可选仅关键字参数 context。 现在Tasks
会自动跟踪其上下文。 详情参见 PEP 567 [https://peps.python.org/pep-0567/]。 (由 Yury Selivanov 在 bpo-32436 [https://bugs.python.org/issue?@action=redirect&bpo=32436] 中贡献。)增加了新的
asyncio.create_task()
函数作为asyncio.get_event_loop().create_task()
的快捷方式。 (由 Andrew Svetlov 在 bpo-32311 [https://bugs.python.org/issue?@action=redirect&bpo=32311] 中贡献。)新的
loop.start_tls()
方法可用于升级现有的 TLS 连接。 (由 Yury Selivanov 在 bpo-23749 [https://bugs.python.org/issue?@action=redirect&bpo=23749] 中贡献。)新的
loop.sock_recv_into()
方法允许直接从套接字读取数据放入所提供的缓冲区,从而可以减少数据复制。 (由 Antoine Pitrou 在 bpo-31819 [https://bugs.python.org/issue?@action=redirect&bpo=31819] 中贡献。)新增的
asyncio.current_task()
函数可返回当前运行的Task
实例,而新增的asyncio.all_tasks()
函数可返回给定循环中所有现存Task
实例的集合。Task.current_task()
和Task.all_tasks()
方法已被弃用。 (由 Andrew Svetlov 在 bpo-32250 [https://bugs.python.org/issue?@action=redirect&bpo=32250] 中贡献。)新的 暂定
BufferedProtocol
类允许通过手动控制接收缓冲区来实现流式协议。 (由 Yury Selivanov 在 bpo-32251 [https://bugs.python.org/issue?@action=redirect&bpo=32251] 中贡献。)新的
asyncio.get_running_loop()
函数可返回当前运行的循环,如果没有循环在运行则引发RuntimeError
。 这与asyncio.get_event_loop()
不同,后者在没有循环在运行时将 创建 一个新的事件循环。 (由 Yury Selivanov 在 bpo-32269 [https://bugs.python.org/issue?@action=redirect&bpo=32269] 中提供。)新的
StreamWriter.wait_closed()
协程方法允许执行等待直到流写入器被关闭。 新的StreamWriter.is_closing()
方法可用于确定写入器是否被关闭。 (由 Andrew Svetlov 在 bpo-32391 [https://bugs.python.org/issue?@action=redirect&bpo=32391] 中贡献。)新的
loop.sock_sendfile()
协程方法允许在可能的情况下使用os.sendfile
发送文件。 (由 Andrew Svetlov 在 bpo-32410 [https://bugs.python.org/issue?@action=redirect&bpo=32410] 中贡献。)新的
Future.get_loop()
和Task.get_loop()
方法会返回创建 task 或 future 对象的事件循环的实例。Server.get_loop()
允许为asyncio.Server
对象执行同样操作。 (由 Yury Selivanov 在 bpo-32415 [https://bugs.python.org/issue?@action=redirect&bpo=32415] 中,以及由 Srinivas Reddy Thatiparthy 在 bpo-32418 [https://bugs.python.org/issue?@action=redirect&bpo=32418] 中贡献。)现在可以控制
asyncio.Server
的实例如何开启服务。 之前,服务在创建后将立即开启服务。 新的 start_serving 关键字参数已添加到loop.create_server()
和loop.create_unix_server()
,并且Server.start_serving()
, 和Server.serve_forever()
可被用来分离服务的实例化和服务的开启。 新的Server.is_serving()
方法会在服务开启时返回True
。 现在Server
对象已是异步上下文管理器:
- srv = await loop.create_server(...)
- async with srv:
- # 一些代码
- # 此时,srv 已关闭并不再接受新的连接。
(由 Yury Selivanov 在 bpo-32662 [https://bugs.python.org/issue?@action=redirect&bpo=32662] 中贡献。)
由
loop.call_later()
所返回的回调对象已获得新的when()
方法,该方法会返回一个排入计划日程的绝对时间戳。 (由 Andrew Svetlov 在 bpo-32741 [https://bugs.python.org/issue?@action=redirect&bpo=32741] 中贡献。)loop.create_datagram_endpoint()
方法已获得对 Unix 套接字的支持。 (由 Quentin Dawans 在 bpo-31245 [https://bugs.python.org/issue?@action=redirect&bpo=31245] 中贡献。)asyncio.open_connection()
,asyncio.start_server()
functions,loop.create_connection()
,loop.create_server()
,loop.create_accepted_socket()
方法及其对应的 UNIX 套接字变体现在接受 ssl_handshake_timeout 关键字参数。 (由 Neil Aspinall 在 bpo-29970 [https://bugs.python.org/issue?@action=redirect&bpo=29970] 中贡献。)新的
Handle.cancelled()
方法会在回调被取消时返回True
。 (由 Marat Sharafutdinov 在 bpo-31943 [https://bugs.python.org/issue?@action=redirect&bpo=31943] 中贡献。)asyncio 源已被转换为使用
async
/await
语法。 (由 Andrew Svetlov 在 bpo-32193 [https://bugs.python.org/issue?@action=redirect&bpo=32193] 中贡献。)新的
ReadTransport.is_reading()
方法可用于确定传输的读取状态。 此外,对ReadTransport.resume_reading()
和ReadTransport.pause_reading()
的调用现在是幂等的。 (由 Yury Selivanov 在 bpo-32356 [https://bugs.python.org/issue?@action=redirect&bpo=32356] 中贡献。)接受套接字路径的循环方法现在支持传入 路径类对象。 (由 Yury Selivanov 在 bpo-32066 [https://bugs.python.org/issue?@action=redirect&bpo=32066] 中贡献。)
在
asyncio
中,Linux 上的 TCP 套接字现在创建时默认带有TCP_NODELAY
旗标设置。 (由 Yury Selivanov 和 Victor Stinner 在 bpo-27456 [https://bugs.python.org/issue?@action=redirect&bpo=27456] 中贡献。)在被取消任务中发生的异常不会再被记录。 (由 Yury Selivanov 在 bpo-30508 [https://bugs.python.org/issue?@action=redirect&bpo=30508] 中贡献。)
新的
WindowsSelectorEventLoopPolicy
和WindowsProactorEventLoopPolicy
类。 (由 Yury Selivanov 在 bpo-33792 [https://bugs.python.org/issue?@action=redirect&bpo=33792] 中贡献。)
部分 asyncio
API 改为 已弃用。
binascii
b2a_uu()
函数现在接受可选的 backtick 关键字参数。 当其为真值时,零会以 '`'
而非空格来表示。 (由 Xiang Zhang 在 bpo-30103 [https://bugs.python.org/issue?@action=redirect&bpo=30103] 中贡献。)
calendar
HTMLCalendar
类具有新的类属性,可以简化所生成 HTML 日历中 CSS 类的自定义。 (由 Oz Tiram 在 bpo-30095 [https://bugs.python.org/issue?@action=redirect&bpo=30095] 中贡献。)
collections
collections.namedtuple()
现在支持默认值。 (由 Raymond Hettinger 在 bpo-32320 [https://bugs.python.org/issue?@action=redirect&bpo=32320] 中贡献。)
compileall
compileall.compile_dir()
增加了新的 invalidation_mode 形参,可用于启用 基于哈希值的 .pyc 有效性检测。 失效模式也可以在命令行中使用新的 --invalidation-mode
参数来指定。 (由 Benjamin Peterson 在 bpo-31650 [https://bugs.python.org/issue?@action=redirect&bpo=31650] 中贡献。)
concurrent.futures
ProcessPoolExecutor
和 ThreadPoolExecutor
现在支持新的 初始化器 以及 initargs 构造器参数。 (由 Antoine Pitrou 在 bpo-21423 [https://bugs.python.org/issue?@action=redirect&bpo=21423] 中贡献。)
ProcessPoolExecutor
现在能通过新的 mp_context 参数来接受多进程上下文。 (由 Thomas Moreau 在 bpo-31540 [https://bugs.python.org/issue?@action=redirect&bpo=31540] 中贡献。)
contextlib
新的 nullcontext()
是一个比 ExitStack
更简单和快速的无操作上下文管理器。 (由 Jesse-Bakker 在 bpo-10049 [https://bugs.python.org/issue?@action=redirect&bpo=10049] 中贡献。)
增加了新的 asynccontextmanager()
, AbstractAsyncContextManager
和 AsyncExitStack
以补充它们所对应的同步项。 (由 Jelle Zijlstra 在 bpo-29679 [https://bugs.python.org/issue?@action=redirect&bpo=29679] 和 bpo-30241 [https://bugs.python.org/issue?@action=redirect&bpo=30241] 中,以及由 Alexander Mohr 和 Ilya Kulakov 在 bpo-29302 [https://bugs.python.org/issue?@action=redirect&bpo=29302] 中贡献。)
cProfile
cProfile
命令行现在接受 -m module_name
作为脚本路径的替代。 (由 Sanyam Khurana 在 bpo-21862 [https://bugs.python.org/issue?@action=redirect&bpo=21862] 中贡献。)
crypt
现在 crypt
模块已支持 Blowfish 哈希算法。 (由 Serhiy Storchaka 在 bpo-31664 [https://bugs.python.org/issue?@action=redirect&bpo=31664] 中贡献。)
现在 mksalt()
函数允许指定哈希操作的轮数。 (由 Serhiy Storchaka 在 bpo-31702 [https://bugs.python.org/issue?@action=redirect&bpo=31702] 中贡献。)
datetime
新的 datetime.fromisoformat()
方法会基于由 datetime.isoformat()
所输出的某一特定格式字符串构建 datetime
对象。 (由 Paul Ganssle 在 bpo-15873 [https://bugs.python.org/issue?@action=redirect&bpo=15873] 中贡献。)
tzinfo
类现在支持小于一分钟的偏移量。 (由 Alexander Belopolsky 在 bpo-5288 [https://bugs.python.org/issue?@action=redirect&bpo=5288] 中贡献。)
dbm
dbm.dumb
现在支持读取只读文件,并且在其未改变时不再写入索引文件。
decimal
decimal
模块现在使用 上下文变量 来储存十进制值上下文。 (由 Yury Selivanov 在 bpo-32630 [https://bugs.python.org/issue?@action=redirect&bpo=32630] 中贡献。)
dis
dis()
函数现在能够反汇编嵌套的代码对象(推导式、生成器表达式和嵌套函数的代码,以及用于构建嵌套类的代码)。 反汇编递归的最大深度由新的 depth 形参来控制。 (由 Serhiy Storchaka 在 bpo-11822 [https://bugs.python.org/issue?@action=redirect&bpo=11822] 中贡献。)
distutils
README.rst
现在包含在 distutils 的标准 README 列表之中,因而也包含在源码发布之中。 (由 Ryan Gonzalez 在 bpo-11913 [https://bugs.python.org/issue?@action=redirect&bpo=11913] 中贡献。)
enum
Enum
增加了新的 ignore
类特征属性,该属性允许列出不应当成为枚举成员的特征属性名称。 (由 Ethan Furman 在 bpo-31801 [https://bugs.python.org/issue?@action=redirect&bpo=31801] 中贡献。)
在 Python 3.8 中,尝试在 Enum
类中检查非 Enum 对象将引发 TypeError
(例如 1 in Color
);类似地,尝试在 Flag
成员中检查非 Flag 对象也将引发 TypeError
(例如 1 in Perm.RW
);目前,两种操作均会返回 False
并且已弃用。 (由 Ethan Furman 在 bpo-33217 [https://bugs.python.org/issue?@action=redirect&bpo=33217] 中贡献。)
functools
functools.singledispatch()
现在支持使用类型标注来注册实现。 (由 Łukasz Langa 在 bpo-32227 [https://bugs.python.org/issue?@action=redirect&bpo=32227] 中贡献。)
gc
新的 gc.freeze()
函数允许冻结由垃圾回收器所跟踪的所有对象,并将它们从未来的集合中排除。 这可以在 POSIX fork()
调用之前使用以令 GC 友好地进行写入时复制或加速收集。 新的 gc.unfreeze()
函数会反转此操作。 此外,gc.get_freeze_count()
可被用于获取冻结对象的数量。 (由 Li Zekun 在 bpo-31558 [https://bugs.python.org/issue?@action=redirect&bpo=31558] 中贡献。)
hmac
hmac
现在具有经优化的一次性 digest()
函数,其速度比 HMAC()
要快三倍。 (由 Christian Heimes 在 bpo-32433 [https://bugs.python.org/issue?@action=redirect&bpo=32433] 中贡献。)
http.client
HTTPConnection
和 HTTPSConnection
现在支持新的 blocksize 参数以提升上传吞吐量。 (由 Nir Soffer 在 bpo-31945 [https://bugs.python.org/issue?@action=redirect&bpo=31945] 中贡献。)
http.server
SimpleHTTPRequestHandler
现在支持 HTTP If-Modified-Since
标头。 如果目标文件在该标点指定的时间之后未被修改则服务器会返回 304 响应状态。 (由 Pierre Quentel 在 bpo-29654 [https://bugs.python.org/issue?@action=redirect&bpo=29654] 中贡献。)
SimpleHTTPRequestHandler
接受新的 directory 参数并增加了新的 --directory
命令行参数。 通过此形参,服务器可以对服务指定目录,默认情况下它使用当前工作目录。 (由 Stéphane Wirtel 和 Julien Palard 在 bpo-28707 [https://bugs.python.org/issue?@action=redirect&bpo=28707] 中贡献。)
新的 ThreadingHTTPServer
类使用线程来处理使用 ThreadingMixin
的请求。 它会在 http.server
附带 -m
运行时被使用。 (由 Julien Palard 在 bpo-31639 [https://bugs.python.org/issue?@action=redirect&bpo=31639] 中贡献。)
idlelib 与 IDLE
多个对自动补全的修正。 (由 Louie Lu 在 bpo-15786 [https://bugs.python.org/issue?@action=redirect&bpo=15786] 中贡献。)
Module Browser (在 File 菜单中,之前称为 Class Browser) 现在会在最高层级函数和类之外显示嵌套的函数和类。 (由 Guilherme Polo, Cheryl Sabella 和 Terry Jan Reedy 在 bpo-1612262 [https://bugs.python.org/issue?@action=redirect&bpo=1612262] 中贡献。)
Settings 对话框 (Options 中的 Configure IDLE) 已经被部分重写以改进外观和功能。 (由 Cheryl Sabella 和 Terry Jan Reedy 在多个问题项中贡献。)
字体样本现在包括一组非拉丁字符以便用户能更好地查看所选特定字体的效果。 (由 Terry Jan Reedy 在 bpo-13802 [https://bugs.python.org/issue?@action=redirect&bpo=13802] 中贡献。) 样本可以被修改以包括其他字符。 (由 Serhiy Storchaka 在 bpo-31860 [https://bugs.python.org/issue?@action=redirect&bpo=31860] 中贡献。)
之前以扩展形式实现的 IDLE 特性已作为正常特性重新实现。 它们的设置已从 Extensions 选项卡移至其他对话框选项卡。 (由 Charles Wohlganger 和 Terry Jan Reedy 在 bpo-27099 [https://bugs.python.org/issue?@action=redirect&bpo=27099] 中实现。)
编辑器代码上下文选项已经过修改。 Box 会显示所有上下文行直到最大行数。 点击一个上下文行会使编辑器跳转到该行。 自定义主题的上下文颜色已添加到 Settings 对话框的 Highlights 选项卡。 (由 Cheryl Sabella 和 Terry Jan Reedy 在 bpo-33642 [https://bugs.python.org/issue?@action=redirect&bpo=33642], bpo-33768 [https://bugs.python.org/issue?@action=redirect&bpo=33768] 和 bpo-33679 [https://bugs.python.org/issue?@action=redirect&bpo=33679] 中贡献。)
在 Windows 上,会有新的 API 调用将 tk 对 DPI 的调整告知 Windows。 在 Windows 8.1+ 或 10 上,如果 Python 二进制码的 DPI 兼容属性未改变,并且监视器分辨率大于 96 DPI,这应该会令文本和线条更清晰。 否则的话它应该不造成影响。 (由 Terry Jan Reedy 在 bpo-33656 [https://bugs.python.org/issue?@action=redirect&bpo=33656] 中贡献。)
在 3.7.1 中新增:
超过 N 行(默认值为 50)的输出将被折叠为一个按钮。 N 可以在 Settings 对话框的 General 页的 PyShell 部分中进行修改。 数量较少但是超长的行可以通过在输出上右击来折叠。 被折叠的输出可通过双击按钮来展开,或是通过右击按钮来放入剪贴板或是单独的窗口。 (由 Tal Einat 在 bpo-1529353 [https://bugs.python.org/issue?@action=redirect&bpo=1529353] 中贡献。)
上述修改已被反向移植到 3.6 维护发行版中。
在 3.7.4 中新增:
在 Run 菜单中增加了 "Run Customized" 以使用自定义设置来运行模块。 输入的任何命令行参数都会被加入 sys.argv。 它们在下次自定义运行时会再次显示在窗体中。 用户也可以禁用通常的 Shell 主模块重启。 (由 Cheryl Sabella, Terry Jan Reedy 等人在 bpo-5680 [https://bugs.python.org/issue?@action=redirect&bpo=5680] 和 bpo-37627 [https://bugs.python.org/issue?@action=redirect&bpo=37627] 中贡献。)
在 3.7.5 中新增:
在 IDLE 编辑器窗口中增加了可选的行序号。 窗口打开时默认不带行序号,除非在配置对话框的 General 选项卡中进行设置。 已打开窗口中的行序号可以在 Options 菜单中显示和隐藏。 (由 Tal Einat 和 Saimadhav Heblikar 在 bpo-17535 [https://bugs.python.org/issue?@action=redirect&bpo=17535] 中贡献。)
importlib
引入了 importlib.abc.ResourceReader
ABC 以支持从包中加载资源。 另请参阅 importlib.resources。 (由 Barry Warsaw, Brett Cannon 在 bpo-32248 [https://bugs.python.org/issue?@action=redirect&bpo=32248] 中贡献。)
如果模块缺少规格描述 importlib.reload()
现在会引发 ModuleNotFoundError
。 (由 Garvit Khatri 在 bpo-29851 [https://bugs.python.org/issue?@action=redirect&bpo=29851] 中贡献。)
如果指定的父模块不是一个包 (即缺少 __path__
属性) importlib.find_spec()
现在会引发 ModuleNotFoundError
而非 AttributeError
。 (由 Milan Oberkirch 在 bpo-30436 [https://bugs.python.org/issue?@action=redirect&bpo=30436] 中贡献。)
新的 importlib.source_hash()
可被用来计算传入源的哈希值。 基于哈希值的 .pyc 文件 会嵌入此函数所返回的值。
io
新的 TextIOWrapper.reconfigure()
方法可用于根据新的设置重新配置文本流。 (由 Antoine Pitrou 在 bpo-30526 [https://bugs.python.org/issue?@action=redirect&bpo=30526] 以及 INADA Naoki 在 bpo-15216 [https://bugs.python.org/issue?@action=redirect&bpo=15216] 中贡献。)
ipaddress
methods of ipaddress.IPv6Network
和 ipaddress.IPv4Network
中新的 subnet_of()
以及 supernet_of()
方法可用于网络包含测试。 (由 Michel Albert 和 Cheryl Sabella 在 bpo-20825 [https://bugs.python.org/issue?@action=redirect&bpo=20825] 中贡献。)
itertools
itertools.islice()
现在接受 类整数对象
作为 start, stop 和 slice 参数。 (由 Will Roberts 在 bpo-30537 [https://bugs.python.org/issue?@action=redirect&bpo=30537] 中贡献。)
locale
locale.format_string()
中新的 monetary 参数可用于转换所使用的千位分隔符和分组字符串。 (由 Garvit 在 bpo-10379 [https://bugs.python.org/issue?@action=redirect&bpo=10379] 中贡献。)
现在 locale.getpreferredencoding()
函数在 Android 上或是在 强制 UTF-8 模式 下总是返回 'UTF-8'
。
logging
Logger
实例现在可以被 pickle。 (由 Vinay Sajip 在 bpo-30520 [https://bugs.python.org/issue?@action=redirect&bpo=30520] 中贡献。)
新的 StreamHandler.setStream()
方法可用于在句柄创建之后替换日志流。 (由 Vinay Sajip 在 bpo-30522 [https://bugs.python.org/issue?@action=redirect&bpo=30522] 中创建。)
现在可以在传递给 logging.config.fileConfig()
的配置信息中对句柄构造器指定关键字参数。 (由 Preston Landers 在 bpo-31080 [https://bugs.python.org/issue?@action=redirect&bpo=31080] 中贡献。)
math
新的 math.remainder()
函数实现了 IEEE 754 风格的余数运算。 (由 Mark Dickinson 在 bpo-29962 [https://bugs.python.org/issue?@action=redirect&bpo=29962] 中贡献。)
mimetypes
.bmp 的 MIME type 从 'image/x-ms-bmp'
改为 'image/bmp'
。 (由 Nitish Chandra 在 bpo-22589 [https://bugs.python.org/issue?@action=redirect&bpo=22589] 中贡献。)
msilib
新增的 Database.Close()
方法可被用来关闭 MSI 数据库。 (由 Berker Peksag 在 bpo-20486 [https://bugs.python.org/issue?@action=redirect&bpo=20486] 中贡献。)
multiprocessing
新的 Process.close()
方法会显式地关闭进程对象并释放与其关联的所有资源。 如果底层进程仍在运行则将引发 ValueError
。 (由 Antoine Pitrou 在 bpo-30596 [https://bugs.python.org/issue?@action=redirect&bpo=30596] 中贡献。)
新的 Process.kill()
方法可用于在 Unix 上使用 SIGKILL
信号来终止进程。 (由 Vitor Pereira 在 bpo-30794 [https://bugs.python.org/issue?@action=redirect&bpo=30794] 中贡献。)
由 Process
所创建的非守护线程现在会在进程退出时被合并。 (由 Antoine Pitrou 在 bpo-18966 [https://bugs.python.org/issue?@action=redirect&bpo=18966] 中贡献。)
os
os.fwalk()
现在接受 bytes
类型的 path 参数。 (由 Serhiy Storchaka 在 bpo-28682 [https://bugs.python.org/issue?@action=redirect&bpo=28682] 中贡献。)
os.scandir()
已获得对 文件描述器 的支持。 (由 Serhiy Storchaka 在 bpo-25996 [https://bugs.python.org/issue?@action=redirect&bpo=25996] 中贡献。)
新的 register_at_fork()
函数允许注册 Python 回调以便在进程分叉中执行。 (由 Antoine Pitrou 在 bpo-16500 [https://bugs.python.org/issue?@action=redirect&bpo=16500] 中贡献。)
增加了 os.preadv()
(结合了 os.readv()
与 os.pread()
的功能) 以及 os.pwritev()
函数 (结合了 os.writev()
和 os.pwrite()
的功能)。 (由 Pablo Galindo 在 bpo-31368 [https://bugs.python.org/issue?@action=redirect&bpo=31368] 中贡献。)
os.makedirs()
的 mode 参数不再会影响新创建的中间层级目录的权限位。 (由 Serhiy Storchaka 在 bpo-19930 [https://bugs.python.org/issue?@action=redirect&bpo=19930] 中贡献。)
os.dup2()
现在会返回新的文件描述器。 之前,返回的总是 None
。 (由 Benjamin Peterson 在 bpo-32441 [https://bugs.python.org/issue?@action=redirect&bpo=32441] 中贡献。)
在 Solaris 及其派生系统上 os.stat()
所返回的结构现在会包含 st_fstype
属性。 (由 Jesús Cea Avión 在 bpo-32659 [https://bugs.python.org/issue?@action=redirect&bpo=32659] 中贡献。)
pathlib
在 POSIX 类系统上新的 Path.is_mount()
方法现在可用于确定一个路径是否为挂载点。 (由 Cooper Ry Lees 在 bpo-30897 [https://bugs.python.org/issue?@action=redirect&bpo=30897] 中贡献。)
pdb
pdb.set_trace()
现在接受一个可选的限关键字参数 header。 如果给出,它会在调试开始之前被打印到控制台。 (由 Barry Warsaw 在 bpo-31389 [https://bugs.python.org/issue?@action=redirect&bpo=31389] 中贡献。)
pdb
命令行现在接受 -m module_name
作为对脚本文件的替代。 (由 Mario Corchero 在 bpo-32206 [https://bugs.python.org/issue?@action=redirect&bpo=32206] 中贡献。)
py_compile
py_compile.compile()
— 及其扩展形式 compileall
— 现在会通过无条件地为基于哈希值的有效性验证创建 .pyc
文件来支持 SOURCE_DATE_EPOCH
环境变量。 这样可以确保当 .pyc
文件被主动创建时 可重现的生成 [https://reproducible-builds.org/]。 (由 Bernhard M. Wiedemann 在 bpo-29708 [https://bugs.python.org/issue?@action=redirect&bpo=29708] 中贡献。)
pydoc
pydoc 服务器现在可以绑定到由新的 -n
命令行参数所指定的任意主机名。 (由 Feanil Patel 在 bpo-31128 [https://bugs.python.org/issue?@action=redirect&bpo=31128] 中贡献。)
queue
新的 SimpleQueue
类是一个无界的 FIFO 队列。 (由 Antoine Pitrou 在 bpo-14976 [https://bugs.python.org/issue?@action=redirect&bpo=14976] 中贡献。)
re
旗标 re.ASCII
, re.LOCALE
和 re.UNICODE
可以在组的范围内设置。 (由 Serhiy Storchaka 在 bpo-31690 [https://bugs.python.org/issue?@action=redirect&bpo=31690] 中贡献。)
re.split()
现在支持基于匹配一个空字符串的模式例如 r'\b'
, '^$'
或 (?=-)
进行拆分。 (由 Serhiy Storchaka 在 bpo-25054 [https://bugs.python.org/issue?@action=redirect&bpo=25054] 中贡献。)
使用 re.LOCALE
旗标编译的正则表达式不再依赖于编译时的区域设置。 区域设置仅在已编译正则表达式被使用时才被应用。 (由 Serhiy Storchaka 在 bpo-30215 [https://bugs.python.org/issue?@action=redirect&bpo=30215] 中贡献。)
现在如果一个正则表达式包含语义将在未来发生改变的字符集构造,则会引发 FutureWarning
,例如嵌套集与集合操作等。 (由 Serhiy Storchaka 在 bpo-30349 [https://bugs.python.org/issue?@action=redirect&bpo=30349] 中贡献。)
已编译正则表达式和匹配对象现在可以使用 copy.copy()
和 copy.deepcopy()
进行拷贝。 (由 Serhiy Storchaka 在 bpo-10076 [https://bugs.python.org/issue?@action=redirect&bpo=10076] 中贡献。)
signal
signal.set_wakeup_fd()
函数新增的 warn_on_full_buffer 参数可以指定当唤醒缓冲区溢出时 Python 是否要在 stderr 上打印警告信息。 (由 Nathaniel J. Smith 在 bpo-30050 [https://bugs.python.org/issue?@action=redirect&bpo=30050] 中贡献。)