[英]SQLAlchemy: Use column from outer query in subquery
我有这个(MSSQL)查询,我想将其转换为SQLAlchemy:
SELECT * FROM Artikel AS root WHERE (SELECT COUNT(*) FROM Artikel WHERE Artikel.MM_ParentID = root.ROW_ID) = 0 AND MM_ParentID = 0;
这是我尝试的:
root = sqlalchemy.orm.aliased(GSDArtikel, name='root')
parent_count_query = gsd_session.query(sqla.func.count()).select_from(GSDArtikel).filter(GSDArtikel.MM_ParentID == root.row_id)
results = gsd_session.query(root).filter((parent_count_query == 0) & (root.MM_ParentID == 0))
但是, parent_count_query == 0
生成布尔值,这将导致失败:
TypeError: unsupported operand type(s) for &: 'bool' and 'BinaryExpression'
parent_count_query
有型sqlalchemy.orm.query.Query
。
我也尝试添加.subquery()
这类型更改为sqlalchemy.sql.selectable.Alias
,但还是给了我False
的比较时。
当我打印生成的内部查询时,它看起来不太像我期望的那样:
SELECT count(*) AS count_1
FROM [Artikel], [Artikel] AS root
WHERE [Artikel].[MM_ParentID] = root.row_id
我也尝试使用sqla.and_(parent_count_query == 0, root.MM_ParentID == 0)
代替&
-然后我没有得到TypeError
,而是得到以下SQL以获得results
:
SELECT ...
FROM [Artikel] AS root
WHERE 0 = 1
我究竟做错了什么?
我有一个带有根行和子行的表,基本上是这样的:
| row_id | MM_ParentID |
------------------------
| 1 | 0 |
| 2 | 0 |
| 3 | 0 |
| 4 | 1 |
| 5 | 1 |
| 6 | 3 |
我想找到的是所有属于父级( MM_ParentID == 0
)并且没有子级的行(子查询将获得所有MM_ParentID
等于当前项的row_id
的子级的子查询返回0行)。 因此,在这种情况下,将返回具有row_id
2的项目。
您的问题是您无法在sqlalchemy
构建子查询,然后只能像在纯SQL
那样比较结果。
无论如何,如果我正确理解了您的问题,我会以其他方式解决它; 首先获取确实有父母的文章,
In [39]:
from sqlalchemy.orm import aliased
root = aliased(Article, name='root')
subq = session.query(Article.id).select_from(Article).filter(Article.parent_id == root.id)
print(subq)
SELECT article.id AS article_id
FROM article, article AS root
WHERE article.parent_id = root.id
然后寻找像这样的基础文章:
In [40]:
from sqlalchemy import tuple_
results = session.query(Article).filter(~Article.id.in_(subq))
print(results)
SELECT article.id AS article_id, article.parent_id AS article_parent_id
FROM article
WHERE article.id NOT IN (SELECT article.id AS article_id
FROM article AS root
WHERE article.parent_id = root.id)
当然,还有其他方法。 这是我想出的简单方法,如果您的桌子很大,可能不是最佳选择。 (很抱歉,我为您的表名和列名使用了不同的拼写!)
希望能帮助到你。
我最终简化了查询,以便将孩子与父母联系起来,然后得到孩子为IS NULL
的孩子:
stray_parents = (gsd_session.query(item)
.outerjoin(child, item.row_id == child.MM_ParentID)
.filter(item.MM_ParentID == 0, child.row_id == None))
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.