sql - 从没有外键的两个模型的 JOIN 中检索值(Django)
问题描述
我想检索与两个不同模型(没有外键)相关的两列的值。在 SQL 中,我会这样写:
SELECT employees.name, companies.name
FROM employees
JOIN companies
ON companies.location=employees.location;
假设这两个模型被称为Employee
和Company
。它们没有共同的外键,我也不能更改模型。
我怎样才能在 Django 中拥有相同的功能?我是否必须编写原始 SQL 查询?
解决方案
我将添加答案作为其他用户的未来参考,因为评论中链接的类似问题不是很详细。
from django.db.models import Subquery, OuterRef
Employee.objects.annotate(
company_name=Subquery(
Company.objects.filter(location=OuterRef('location')).values('name')
)
).values_list('name', 'company_name')
解释
将其分成几部分(从内到外):
1.
OuterRef('location')
这将创建location
对对象属性的引用Employee
。之所以称为Outer Ref,是因为它指的是在子查询(调用子查询)之外使用的模型。
2.
Subquery(Company.objects.filter(location=OuterRef('location')).values('name'))
子查询返回与location
员工相同的所有公司的名称。
3.
Employee.objects.annotate(
company_name=Subquery(...)
)
这基本上是Employee
用一个名为company_name
. 此字段存储来自 (2) 的子查询的结果。
生成的 SQL 查询将如下所示:
SELECT employees.name,
(SELECT companies.name
FROM companies
WHERE companies.location = employees.location) AS company_name
FROM employees
(我简化了 Django ORM 产生的一些混乱)。
笔记
重要的是要注意这将使用子查询(而不是连接)。在某些情况下,这可能会影响性能。
推荐阅读
- raspberry-pi - 如何将 Alexa 的自定义技能添加到 Alexa Raspberry Pi?
- java - 在模拟器/真实设备上滚动后无法单击元素
- r - 在组中查找重叠时间
- python - 搅拌机 + Python
- angular - Angular mat select 会覆盖 dropodn 中应显示所选值的文本
- php - 将 PHP splat 参数传递给另一个函数
- python - 在 Selenium Python 中单击 div 下拉列表中的标签,没有任何效果
- sql - 无法打开数据库 XXX;登录请求。登录失败。客户端连接 ID:
- python - Pydroid 3 中的多个绘图是如何制作的,每个绘图都在单独的窗口中?
- spring-kafka - 不能在测试中多次使用 @KafkaListener