使用 isinstance() 或 issubclass() 配合抽象基类(ABC)可判断类型关系:isinstance(obj, ABC) 检查实例是否满足 ABC 接口(要求已实现抽象方法),issubclass(cls, ABC) 仅检查继承或注册关系,不校验实现;鸭子类型可通过 hasattr 动态验证行为存在性。

用 isinstance() 或 issubclass() 配合抽象基类(ABC)即可判断,前提是该 ABC 正确注册或继承了 abc.ABC。
使用 isinstance() 判断实例是否符合 ABC
这是最常用、最直观的方式。只要对象的类是该 ABC 的子类(显式继承或动态注册),且满足所有抽象方法/属性要求,isinstance(obj, MyABC) 就返回 True。
from abc import ABC, abstractmethodclass Drawable(ABC): @abstractmethod def draw(self): pass
class Circle(Drawable): def draw(self): print("Drawing a circle")
c = Circle() print(isinstance(c, Drawable)) # True
注意:如果类未实现抽象方法,实例化时会报错,所以能成功创建实例通常意味着已满足接口要求。
使用 issubclass() 判断类是否属于某 ABC 体系
适用于检查类型定义本身,而非具体对象。它不关心类是否已实现抽象方法,只看继承/注册关系。
立即学习“Python免费学习笔记(深入)”;
- 显式继承:直接写
class A(B): ...→issubclass(A, B)为True - 动态注册:用
MyABC.register(ConcreteClass)后,issubclass(ConcreteClass, MyABC)也为True - 即使
ConcreteClass没有实现抽象方法,注册后issubclass仍返回True;但isinstance会失败(因为实例化时校验)
检查是否“真正支持”——结合 hasattr 或协议式判断(可选补充)
Python 更倾向“鸭子类型”。若不想强依赖 ABC,也可直接检查关键方法是否存在:
if hasattr(obj, 'draw') and callable(getattr(obj, 'draw')):
obj.draw()
这种方式更灵活,不依赖类型系统,适合快速验证行为存在性,但无法保证接口完整性(比如参数签名、返回值语义等)。
常见误区提醒
- 仅定义 ABC 不等于自动约束:必须让具体类继承它或调用
.register(),否则isinstance始终为False -
register()是单向的:注册后不能反向查出哪些类被注册过,也无法触发抽象方法检查 - 内置 ABC(如
collections.abc.Iterable)对鸭子类型友好:只要实现了__iter__,isinstance(obj, Iterable)就为True










