Django orm 子查询 - 不带替换的子句

dbf*_*dbf 3 django django-orm

我需要使用 Django ORM 构建一个查询,在 SQL 中看起来像这样:

select * from A where id not in (select a_id from B where ... )
Run Code Online (Sandbox Code Playgroud)

我尝试使用这样的代码:

ids = B.objects.filter(...)
a_objects = A.object.exclude(id__in=Subquery(ids.values('a__id'))).all()
Run Code Online (Sandbox Code Playgroud)

问题是 Django 生成的查询不是嵌套选择,而是如下所示

select * from A where id not in (1, 2, 3, 4, 5 ....)
Run Code Online (Sandbox Code Playgroud)

where in 子句显式列出了应排除的所有 id,导致结果 sql 在打印到日志中时不可读。是否可以调整此查询,以便使用嵌套选择?

Pav*_*rev 7

所以我看到你的目标是从 B 中获取所有没有外键关系的 A。如果我是对的,那么你可以使用反向查找来做到这一点。

因此,当您这样定义模型时:

class A:
    pass

class B:
    a = ForeignKey(to=a, related_name='bs')
Run Code Online (Sandbox Code Playgroud)

您可以这样过滤它:

A.objects.filter(bs__isnull=True)
Run Code Online (Sandbox Code Playgroud)

另外,如果您不定义related_name,它将默认为b_set,因此您将能够A.objects.filter(b_set__isnull=True)