Python - isinstance()更深刻的理解


起因經過

今天翻collections.abc的文檔時,我知道list的實例在邏輯上(因為duck typing 鴨子類型)是Container和不能hash的(因為list可變),就試下面的代碼是否能行:

from collections.abc import Container, Hashable

print(isinstance(list(), Container)) # return true

print(isinstance(list(), Hashable)) # return False

我就產生疑惑,問題1來了:list是繼承於object, 而collections.abc.Container是個抽象類,isinstance為什么能正確運行?換另外一句話說,此時我的理解是根據isintance的語義來的,list並沒有繼承這個抽象類,why isintance() works?

class list(object):
   ...

class Container(metaclass=ABCMeta):
    ...

解決

查找isinstance()文檔:

Return true if the object argument is an instance of the classinfo argument, or of a (direct, indirect or virtual) subclass thereof.
問題2來了,什么是virutal subclass? 剛好virutal那里有個超鏈接,點進去
Abstract base classes complement duck-typing by providing a way to define interfaces .... ABCs introduce virtual subclasses, which are classes that don’t inherit from a class but are still recognized by isinstance() and issubclass();

總結

豁然開朗,想起了以前讀的Fluent Python,因為Python沒有interface,抽象類實現了接口,補充了鴨子類型,加上isinstance支持判斷抽象類,所以就可以判斷。
isinstance支持direct(直接繼承), indirect(非直接繼承), virtual(抽象類)。以前對於isinstance的理解只局限在前兩種。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM