collections.abc --- 容器的抽象基類?
3.3 新版功能: 該模塊曾是 collections 模塊的組成部分。
該模塊定義了一些 抽象基類,它們可用于判斷一個具體類是否具有某一特定的接口;例如,這個類是否可哈希,或其是否為映射類。
容器抽象基類?
這個容器模塊提供了以下 ABCs:
抽象基類 |
繼承自 |
抽象方法 |
Mixin 方法 |
|---|---|---|---|
|
|||
|
|||
|
|||
|
|
||
|
|||
|
|
||
|
|||
|
|||
|
|||
|
|
||
|
繼承自 |
||
|
繼承自 |
||
|
|
||
|
繼承自 |
||
|
|
||
|
繼承自 |
||
|
|||
|
|||
|
|||
|
|||
|
|||
|
|
||
|
|||
|
|
||
|
|
-
class
collections.abc.Container? -
class
collections.abc.Hashable? -
class
collections.abc.Sized? -
class
collections.abc.Callable? 分別提供了
__contains__(),__hash__(),__len__()和__call__()方法的抽象基類。
-
class
collections.abc.Iterable? 提供了
__iter__()方法的抽象基類。使用
isinstance(obj, Iterable)可以檢測一個類是否已經注冊到了Iterable或者實現了__iter__()函數,但是無法檢測這個類是否能夠使用__getitem__()方法進行迭代。檢測一個對象是否是 iterable 的唯一可信賴的方法是調用iter(obj)。
-
class
collections.abc.Collection? 集合了 Sized 和 Iterable 類的抽象基類。
3.6 新版功能.
-
class
collections.abc.Iterator? 提供了
__iter__()和__next__()方法的抽象基類。參見 iterator 的定義。
-
class
collections.abc.Reversible? 為可迭代類提供了
__reversed__()方法的抽象基類。3.6 新版功能.
-
class
collections.abc.Generator? 生成器類,實現了 PEP 342 中定義的協議,繼承并擴展了迭代器,提供了
send(),throw()和close()方法。參見 generator 的定義。3.5 新版功能.
-
class
collections.abc.Sequence? -
class
collections.abc.MutableSequence? -
class
collections.abc.ByteString? 只讀且可變的序列 sequences 的抽象基類。
實現筆記:一些混入(Maxin)方法比如
__iter__(),__reversed__()和index()會重復調用底層的__getitem__()方法。因此,如果實現的__getitem__()是常數級訪問速度,那么相應的混入方法會有一個線性的表現;然而,如果底層方法是線性實現(例如鏈表),那么混入方法將會是平方級的表現,這也許就需要被重構了。在 3.5 版更改: index() 方法支持 stop 和 start 參數。
-
class
collections.abc.MappingView? -
class
collections.abc.ItemsView? -
class
collections.abc.KeysView? -
class
collections.abc.ValuesView? 映射及其鍵和值的視圖 views 的抽象基類。
-
class
collections.abc.Awaitable? 為可等待對象 awaitable 提供的類,可以被用于
await表達式中。習慣上必須實現__await__()方法。協程對象 Coroutine 和
Coroutine抽象基類的實例都是這個抽象基類的實例。注解
在 CPython 里,基于生成器的協程(使用
types.coroutine()或asyncio.coroutine()包裝的生成器)都是 可等待對象,即使他們不含有__await__()方法。使用isinstance(gencoro, Awaitable)來檢測他們會返回False。要使用inspect.isawaitable()來檢測他們。3.5 新版功能.
-
class
collections.abc.Coroutine? 用于協程兼容類的抽象基類。實現了如下定義在 協程對象: 里的方法:
send(),throw()和close()。通常的實現里還需要實現__await__()方法。所有的Coroutine實例都必須是Awaitable實例。參見 coroutine 的定義。注解
在 CPython 里,基于生成器的協程(使用
types.coroutine()或asyncio.coroutine()包裝的生成器)都是 可等待對象,即使他們不含有__await__()方法。使用isinstance(gencoro, Coroutine)來檢測他們會返回False。要使用inspect.isawaitable()來檢測他們。3.5 新版功能.
-
class
collections.abc.AsyncIterable? 提供了
__aiter__方法的抽象基類。參見 asynchronous iterable 的定義。3.5 新版功能.
-
class
collections.abc.AsyncIterator? 提供了
__aiter__和__anext__方法的抽象基類。參見 asynchronous iterator 的定義。3.5 新版功能.
這些抽象基類讓我們可以確定類和示例擁有某些特定的函數,例如:
size = None
if isinstance(myvar, collections.abc.Sized):
size = len(myvar)
有些抽象基類也可以用作混入類(mixin),這可以更容易地開發支持容器 API 的類。例如,要寫一個支持完整 Set API 的類,只需要提供下面這三個方法: __contains__(), __iter__() 和 __len__()。抽象基類會補充上其余的方法,比如 __and__() 和 isdisjoint():
class ListBasedSet(collections.abc.Set):
''' Alternate set implementation favoring space over speed
and not requiring the set elements to be hashable. '''
def __init__(self, iterable):
self.elements = lst = []
for value in iterable:
if value not in lst:
lst.append(value)
def __iter__(self):
return iter(self.elements)
def __contains__(self, value):
return value in self.elements
def __len__(self):
return len(self.elements)
s1 = ListBasedSet('abcdef')
s2 = ListBasedSet('defghi')
overlap = s1 & s2 # The __and__() method is supported automatically
當把 Set 和 MutableSet 用作混入類時需注意:
由于某些集合操作會創建新集合,默認的混入方法需要一種從可迭代對象里創建新實例的方法。假如其類構造函數簽名形如
ClassName(iterable),則其會調用一個內部的類方法_from_iterable(),其中調用了cls(iterable)來生成一個新集合。如果這個Set混入類在類中被使用,但其構造函數的簽名卻是不同的形式,那么你就需要重載_from_iterable()方法,將其編寫成一個類方法,并且它能夠從可迭代對象參數中構造一個新實例。重載比較符時時(想必是為了速度,因為其語義都是固定的),只需要重定義
__le__()和__ge__()函數,然后其他的操作會自動跟進。混入集合類
Set提供了一個_hash()方法為集合計算哈希值,然而,__hash__()函數卻沒有被定義,因為并不是所有集合都是可哈希并且不可變的。為了使用混入類為集合添加哈希能力,可以同時繼承Set()和Hashable()類,然后定義__hash__ = Set._hash。
參見
OrderedSet recipe 是基于
MutableSet構建的一個示例。
