首页 > 解决方案 > 类型注释中的 collections.Iterable 与 typing.Iterable 并检查 Iterable

问题描述

我发现在 Python 中两者collections.Iterabletyping.Iterable都可以用于类型注释和检查对象是否可迭代,即两者都isinstance(obj, collections.Iterable)可以使用isinstance(obj, typing.Iterable)。我的问题是,它们之间有什么区别?在哪些情况下首选哪一个?

标签: pythontypesannotationsiterableisinstance

解决方案


typing.Iterable是通用的,因此您可以在类型注释中说明它是可迭代的,例如Iterable[int]对于整数的可迭代。

可迭代的集合是一个抽象基类。这些可以包括额外的 mixin 方法,以便在您创建自己的子类时更容易实现接口。

现在碰巧Iterable不包括任何这些mixin,但它是其他抽象基类的接口的一部分。

从理论上讲,打字迭代适用于任何一种,但它使用了一些奇怪的元类魔法来做到这一点,所以它们在所有情况下的行为方式并不完全相同。您在运行时确实不需要泛型,因此无需在类型注释等之外使用它。可迭代的集合作为超类不太可能引起问题。

所以简而言之,您应该在类型注释中使用类型可迭代,但集合可作为超类迭代。


更新:

由于PEP 585,从 3.9 版开始,Python 的标准库容器类型也将能够接受类型注释的通用参数。这包括collections.abc.Iterable类。当仅支持 Python 3.9 或更高版本时,根本没有任何理由使用typing.Iterable并且不推荐从其中导入任何这些容器类型typing


推荐阅读