issubclass()基于导入的行为更改

时间:2017-10-29 21:30:45

标签: python subclass

我试图弄清楚为什么issubclass()的行为会根据类的导入方式而发生变化。

我有以下设置

proj
|_pkg
  |_ __init__.py
  |_ base.py
  |_ child.py

base.py有

class Base(object):
    pass

child.py有

from base import Base

class Child(Base):
    pass

然后我在shell中执行以下操作:

$export PYTHONPATH='/tmp/proj'
$ipython
In [1]: from pkg.base import Base as Base1

In [2]: from base import Base as Base2

In [3]: from pkg.child import Child as Child1

In [4]: from child import Child as Child2

In [5]: issubclass(Child1, Base1)
Out[5]: True # Makes Sense

In [6]: issubclass(Child1, Base2)
Out[6]: False # Confused. Why would this be False.

In [7]: issubclass(Child2, Base1)
Out[7]: False # Confused. Why would this be False.

In [8]: issubclass(Child2, Base2)
Out[8]: True

我对In [6]和[7]中发生的事情感到困惑。我希望那些也是True

1 个答案:

答案 0 :(得分:1)

经过一番挖掘后找到答案 - http://python-notes.curiousefficiency.org/en/latest/python_concepts/import_traps.html#the-double-import-trap

  

这个下一个陷阱存在于所有当前版本的Python中,包括   3.3,可以总结为以下一般准则:“永远不要直接添加包目录,或包内的任何目录,直接   到Python路径“。

     

这是有问题的原因是该目录中的每个模块   现在可以通过两个不同的名称访问:作为顶部   level模块(因为目录在sys.path上)和子模块   包(如果包含包的更高级目录)   本身也在sys.path上。

     

作为一个例子,Django(包括版本1.3)曾经是   为特定地点设置确切的这种情况   应用程序 - 应用程序最终可以作为两个应用程序访问   和site.app在模块名称空间中,这些实际上是两个   该模块的不同副本。