如何(在运行时)检查一个类是否是另一个类的子类?

时间:2011-02-06 11:26:02

标签: python subclass assert

假设我有一套西装和四个西装子类:Heart,Spade,Diamond,Club。

class Suit:
   ...
class Heart(Suit):
   ...
class Spade(Suit):
   ...
class Diamond(Suit):
   ...
class Club(Suit):
   ...

我有一个接收套装作为参数的方法,它是一个类对象,而不是一个实例。更确切地说,它可能只收到四个值中的一个:Heart,Spade,Diamond,Club。我怎样才能做出确保这样的事情的断言?类似的东西:

def my_method(suit):
   assert(suit subclass of Suit)
   ...

我正在使用Python 3。

9 个答案:

答案 0 :(得分:184)

您可以issubclass()使用此assert issubclass(suit, Suit)

答案 1 :(得分:39)

issubclass(class, classinfo)

摘录:

  

如果class是子类(直接,间接或虚拟),则返回true   classinfo

答案 2 :(得分:25)

如果您有实例,则可以使用isinstance;如果您有课程,则可以使用issubclass。通常认为这是个坏主意。通常在Python中,如果某个对象能够通过尝试对其进行操作来解决问题,那么就可以解决这个问题。

答案 3 :(得分:19)

如果给定的子类issubclass(sub, sup)确实是超类sub的子类,则sup布尔函数返回true。

答案 4 :(得分:1)

您可以使用内置的issubclass。但是类型检查通常被认为是不必要的,因为你可以使用duck-typing。

答案 5 :(得分:1)

使用issubclass似乎是一种写日志级别的简洁方法。使用它有点奇怪......但它似乎比其他选择更清洁。

class Error(object): pass
class Warn(Error): pass
class Info(Warn): pass
class Debug(Info): pass

class Logger():
    LEVEL = Info

    @staticmethod
    def log(text,level):
        if issubclass(Logger.LEVEL,level):
            print(text)
    @staticmethod
    def debug(text):
        Logger.log(text,Debug)   
    @staticmethod
    def info(text):
        Logger.log(text,Info)
    @staticmethod
    def warn(text):
        Logger.log(text,Warn)
    @staticmethod
    def error(text):
        Logger.log(text,Error)

答案 6 :(得分:0)

最小的可运行示例

这是一个更完整的示例,其中包含一些断言:

#!/usr/bin/env python3

class Base:
    pass

class Derived(Base):
    pass

base = Base()
derived = Derived()

# Basic usage.
assert issubclass(Derived, Base)
assert not issubclass(Base, Derived)

# True for same object.
assert issubclass(Base, Base)

# Cannot use object of class.
try:
    issubclass(derived, Base)
except TypeError:
    pass
else:
    assert False

# Do this instead.
assert isinstance(derived, Base)

GitHub upstream

在Python 3.5.2。中进行了测试

答案 7 :(得分:0)

根据Python doc,我们还可以使用class.__mro__属性或class.mro()方法:

class Suit:
    pass
class Heart(Suit):
    pass
class Spade(Suit):
    pass
class Diamond(Suit):
    pass
class Club(Suit):
    pass

>>> Heart.mro()
[<class '__main__.Heart'>, <class '__main__.Suit'>, <class 'object'>]
>>> Heart.__mro__
(<class '__main__.Heart'>, <class '__main__.Suit'>, <class 'object'>)

Suit in Heart.mro()  # True
object in Heart.__mro__  # True
Spade in Heart.mro()  # False

答案 8 :(得分:-5)

#issubclass(child,parent)

class a:
    pass
class b(a):
    pass
class c(b):
    pass

print(issubclass(c,b))#it returns true