如何编写依赖于子关系中的列的混合属性?

def*_*cal 5 python sql sqlalchemy

假设父母和孩子有两张桌子(使用SQLAlchemy):

class Child(Base):
     __tablename__ = 'Child'
     id = Column(Integer, primary_key=True) 
     is_boy = Column(Boolean, default=False)
     parent_id = Column(Integer, ForeignKey('Parent.id'))


class Parent(Base):
     __tablename__ = 'Parent'
     id = Column(Integer, primary_key=True) 
     children = relationship("Child", backref="parent")
Run Code Online (Sandbox Code Playgroud)

如何查询房产是否父母是否有孩子?希望在pandas中使用此列但不确定如何有效地查询它.我的直觉是创建一个SQLALchemy混合属性has_a_boy_child,但我不确定如何定义混合属性或匹配表达式.谢谢!

van*_*van 6

按照相关子查询关系混合count示例,我将构建一个返回男孩的属性:

@hybrid_property
def has_a_boy_child(self):
    return any(child.is_boy for child in self.children)

@has_a_boy_child.expression
def has_a_boy_child(cls):
    return (
        select([func.count(Child.id)])
        .where(Child.parent_id == cls.id)
        .where(Child.is_boy == True)
        .label("number_of_boy_children")
    )
Run Code Online (Sandbox Code Playgroud)

你可以这样使用它:

q_has_boys = session.query(Parent).filter(Parent.has_a_boy_child).all()
q_no_boys = session.query(Parent).filter(~Parent.has_a_boy_child).all()
q_attr = session.query(Parent, Parent.has_a_boy_child).all()
Run Code Online (Sandbox Code Playgroud)

更新:如果您确实想要代替boolcount在pandasNonena),您可以按如下所示进行操作:

@has_a_boy_child.expression
def has_a_boy_child(cls):
    return (
        select([
            case([(exists().where(and_(
                Child.parent_id == cls.id,
                Child.is_boy == True,
            )).correlate(cls), True)],
                else_=False,
            ).label("has_boys")
        ])
        .label("number_of_boy_children")
    )
Run Code Online (Sandbox Code Playgroud)