com*_*ver 6 python sqlalchemy python-3.x
我试图遵循上一个与SQLAlchemy相关的问题中显示的设计模式,并打算在多个文件之间共享一个公共Base实例.完全相同的代码适用于python2和python3.
但是,当我在一个模块(称为模型)中移动文件a.py,b.py,c.py和base.py并添加必要的__init__.py文件时,它继续在python2上工作,但随后产生错误在python3上(详情如下).
我有以下文件:
from sqlalchemy.ext.declarative import declarative_base
Base = declarative_base()
Run Code Online (Sandbox Code Playgroud)
from sqlalchemy import *
from base import Base
from sqlalchemy.orm import relationship
class A(Base):
__tablename__ = "A"
id = Column(Integer, primary_key=True)
Bs = relationship("B", backref="A.id")
Cs = relationship("C", backref="A.id")
Run Code Online (Sandbox Code Playgroud)
from sqlalchemy import *
from base import Base
class B(Base):
__tablename__ = "B"
id = Column(Integer, primary_key=True)
A_id = Column(Integer, ForeignKey("A.id"))
Run Code Online (Sandbox Code Playgroud)
from sqlalchemy import *
from base import Base
class C(Base):
__tablename__ = "C"
id = Column(Integer, primary_key=True)
A_id = Column(Integer, ForeignKey("A.id"))
Run Code Online (Sandbox Code Playgroud)
(空)
from sqlalchemy import create_engine
from sqlalchemy.orm import relationship, backref, sessionmaker
from model import base
from model import a
from model import b
from model import c
engine = create_engine("sqlite:///:memory:")
base.Base.metadata.create_all(engine, checkfirst=True)
Session = sessionmaker(bind=engine)
session = Session()
a1 = a.A()
b1 = b.B()
b2 = b.B()
c1 = c.C()
c2 = c.C()
a1.Bs.append(b1)
a1.Bs.append(b2)
a1.Cs.append(c1)
a1.Cs.append(c2)
session.add(a1)
session.commit()
Run Code Online (Sandbox Code Playgroud)
python2的工作原理:
$ python main.py ; echo $?
0
Run Code Online (Sandbox Code Playgroud)
python3错误:
$ python3 main.py ; echo $?
Traceback (most recent call last):
File "main.py", line 7, in <module>
from model import a
File "/home/shale/code/py/try/model/a.py", line 2, in <module>
from base import Base
ImportError: No module named base
1
Run Code Online (Sandbox Code Playgroud)
我最终通过将base.py中的代码放入我的__init__.py文件中解决了这个问题(如下面的一个答案所述),但有没有人知道为什么这会在python3中产生错误但在python2中不会产生错误?首先是什么变化对此负责?
Python 3 默认切换到绝对导入,并禁止不合格的相对导入.这from base import Base条线是如此的重要.
Python 3只会寻找顶级模块; 你没有base顶级模块model.base.使用完整的模块路径,或使用相对限定符:
from .base import Base
Run Code Online (Sandbox Code Playgroud)
在.一开始告诉Python 3中,从当前包导入起点.
您可以通过添加以下内容在Python 2中启用相同的行为:
from __future__ import absolute_import
Run Code Online (Sandbox Code Playgroud)
这是PEP 328引入的更改,from future导入可从Python 2.5开始提供.
| 归档时间: |
|
| 查看次数: |
1549 次 |
| 最近记录: |