SQLAlchemy:如何在一个列表或另一个列表中选择?

时间:2015-12-13 22:04:52

标签: python sqlalchemy

我有一个看起来像这样的课程:

class A(Base):
    __tablename__ = "a";
    id = Column(Integer, primary_key=True)
    stuff = relationship('Stuff', secondary=stuff_a)
    more_stuff = relationship('Stuff', secondary=more_stuff_a)

基本上有两个列表,东西和包含Stuff列表的more_stuff。

我想做一个查询,选择所有在东西列表或more_stuff列表中都有id = X的Stuff的A。

我就是这样做的一个列表:

session.query(A).join(Stuff).filter(Stuff.id==X)

但那不会从more_stuff中获取东西。

1 个答案:

答案 0 :(得分:2)

我认为,如果您有Stuffsqlalchemy之间的两种关系,即使您加入一种关系,也需要明确指定哪一种,或q = ( session .query(A) .join(Stuff, A.stuff) # @note: here you specify the relationship .filter(Stuff.id == X) ) 会正确地投诉。您可以按如下方式执行此操作:

or_

对于两个列表的过滤,您需要在过滤器中使用S1 = aliased(Stuff) S2 = aliased(Stuff) q = ( session .query(A) .join(S1, A.stuff) # S1 will refer to `A.stuff` .join(S2, A.more_stuff) # S2 will refer to `A.more_stuff` .filter(or_(S1.id == X, S2.id == X)) ) 运算符。为了能够引用这两种关系,最简单的方法是为每种关系创建别名(给出不同的名称)。然后代码如下所示:

relationship.any()

或者,可以使用q = ( session .query(A) .filter(or_( A.stuff.any(Stuff.id == X), # here Stuff will refer to `A.stuff` A.more_stuff.any(Stuff.id == X), # here Stuff will refer to `A.more_stuff` )) )

来实现 clean 代码
EXISTS

但是您需要比较两个版本之间的性能差异,因为后者是使用带有子选择的{{1}}实现的。