码迷,mamicode.com
首页 > 数据库 > 详细

flask_SQLALchemy之多表查询

时间:2019-04-12 21:56:18      阅读:283      评论:0      收藏:0      [点我收藏+]

标签:需要   生成   ==   import   name   外键   res   应该   googl   

1. join 查询

假设这样一个业务场景,知道一个邮箱地址,要查询这个地址所属的用户,第一个办法是用连接多个 filter() 来查询。

for u, a in session.query(User, Address).filter(User.id==Address.user_id).filter(Address.email_address==jack@google.com).all():
     
print(u)
print(a)

# 执行结果
jack
jack@google.com

更简便的方法是使用 join() 方法:

u = session.query(User).join(Address).filter(Address.email_address==jack@google.com).one()
     
print(u)     
# 执行结果
jack

Query.join() 知道如何在 UserAddress 之间进行连接,因为我们设定了外键。假如我们没有指定外键,比如这样:

class User(Base):
__tablename__ = users
id = Column(Integer, primary_key=True)
name = Column(String(50))
fullname = Column(String(50))
password = Column(String(12))
     
     
class Address(Base):
 __tablename__ = addresses
id = Column(Integer, primary_key=True)
email_address = Column(String, nullable=False)
user_id = Column(Integer)

我们可以用下面方法来让 join 生效:

query.join(Address, User.id==Address.user_id) # explicit condition
query.join(User.addresses) # specify relationship from left to right
query.join(Address, User.addresses) # same, with explicit target
query.join(addresses) # same, using a string

例子:

session.query(User).join(Address, User.id==Address.user_id).filter(Address.email_address==jack@google.com).all()

2. 子查询(subquery)

现在需要查询每个用户所拥有的邮箱地址数量,思路是先对 addresses 表按用户 ID 分组,统计各组数量,这样我们得到一张新表;然后用 JOIN 连接新表和 users 两个表,在这里,我们应该使用 LEFT OUTER JOIN,因为使用 INTER JOIN 所得出的新表只包含两表的交集。

 

如果上面的暂时看不懂,我们先来看看第一个 stmt 的情况。

from sqlalchemy.sql import func
     
stmt = session.query(Address.user_id, func.count(*).label(address_count)).group_by(Address.user_id).all()
     
for i in stmt:
print(i)
     
# 执行结果
(5, 2)

 

可以理解成 group_by() 方法生成了一张新的表,该表有两列,第一列是 user_id ,第二列是该 user_id 所拥有的 addresses 的数量,这个值由 func() 跟着的方法产生,我们可以使用 c() 方法来访问这个值。

from sqlalchemy.sql import func
     
stmt = session.query(Address.user_id, func.count(*).label(address_count)).group_by(Address.user_id).subquery()
     
q = session.query(User, stmt.c.address_count).outerjoin(stmt, User.id==stmt.c.user_id).order_by(User.id).all()
     
for i in q:
print(i)
     
# 执行结果
(ed, None)
(wendy, None)
(mary, None)
(fred, None)
(jack, 2)

如果不用 outerjoin() 而使用 join(),就等于使用 SQL 中的 INTER JOIN,所得出的表只为两者交集,不会包含 None 值的列。

from sqlalchemy.sql import func
     
stmt = session.query(Address.user_id, func.count(*).label(address_count)).group_by(Address.user_id).subquery()
     
q = session.query(User, stmt.c.address_count).join(stmt, User.id==stmt.c.user_id).order_by(User.id).all()
     
for i in q:
print(i)
     
# 执行结果
(jack, 2)

 

flask_SQLALchemy之多表查询

标签:需要   生成   ==   import   name   外键   res   应该   googl   

原文地址:https://www.cnblogs.com/moying-wq/p/10698783.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!