繁体   English   中英

带外部联接的sqlalchemy中的order_by

[英]Order_by in sqlalchemy with outer join

我有以下sqlalchemy查询:

score = Scores.query.group_by(Scores.email).order_by(Scores.date).subquery()
students = db.session.query(Students, score.c.id).filter_by(archive=0).order_by(Students.exam_date).outerjoin(score, Students.email == score.c.email)

然后我用以下方法渲染事物:

return render_template('students.html', students=students.all())

现在,问题是我希望显示学生的最后分数,因为其中有许多对应于每个用户。 但是第一个似乎已返回。 我在第一个查询中尝试了一些排序和order_by,但没有成功。

我如何影响和选择“得分”中的最新结果,才能与“学生”中的相应行配对?

谢谢!

首先,您要确保子查询仅为特定学生选择行。 您可以使用correlate方法来做到这一点:

score = db.session.query(Scores.id).order_by(Scores.date.desc()).correlate(Students)

仅此一项无济于事,因为您无法访问学生。 的想法correlate是,如果你使用Students在你的子查询,它不会将它添加到FROM列表,而是依赖于外部查询提供它。 现在,您将要优化查询(如果需要,可以加入条件):

score = score.filter(Students.email == Scores.email)

这将产生一个子查询,每次仅返回单个学生的分数。 剩下的问题是,每个学生是否必须获得多个分数。 如果是这样,则需要对其进行限制(如果没有,则也不需要上面的order_by部分):

score = score.limit(1)

现在,您已确保查询返回单个标量值。 由于您是在选择上下文中使用查询,因此需要将其转换为标量值:

students = db.session.query(Students, score.as_scalar()).filter_by(archive=0).order_by(Students.exam_date)

as_scalar方法是一种告诉SQLAlchemy的方法,该方法返回单个行和一列 因为否则您将无法选择它。

注意 :如果您as_scalar ,我不确定100%是否需要该limit 尝试一下并到期。 如果每个学生只有一个分数,那么您完全不必担心这些东西。

关于此方法的一些提示: Query实例本身就是可迭代的。 这意味着只要您不打印它或类似的东西,就可以像列表一样传递查询,唯一的例外是它只能在访问时(懒惰)运行,并且可以动态优化它,例如可以切片it: students[:10]只会选择前10个学生(如果您在查询中执行此操作,它将以LIMIT执行而不是切片列表,前者效率更高)。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM