Django查询过滤器在Postgres数据库中使用大量ID的ids
问题描述:
我想在Django中将查询传递给PostgreSQL数据库。当我使用大量的ID过滤我的查询时,查询非常缓慢并且上升到70s。Django查询过滤器在Postgres数据库中使用大量ID的ids
寻找一个答案,我看到this post这给出了一个解决我的问题后,只需通过VALUES (id1), (id2), ...
改变ARRAY [ids]
在IN声明。
我测试的解决方案与pgAdmin的原始查询,查询变为从70年代到300毫秒......
我如何可以做同样的命令(即不使用一组ID但值的查询)在Django?
答
诀窍是变换阵列到设置不知何故。
代替(这种形式只有很短的阵列良):
SELECT * FROM tbl t WHERE t.tbl_id = ANY($1); -- WHERE t.tbl_id IN($1); -- equivalent
$1
是所述数组参数。
你仍然可以通过一个数组像你一样,但不加入和加入。像:
SELECT *
FROM tbl t
JOIN unnest($1) arr(id) ON arr.id = t.tbl_id;
或者你可以保持您的查询,也不过替换子查询的阵列unnesting它:
SELECT * FROM tbl t
WHERE t.tbl_id = ANY (SELECT unnest($1));
或者:
SELECT * FROM tbl t
WHERE t.tbl_id IN (SELECT unnest($1));
的性能传球效果相同a 设置与VALUES
表达。但传递数组通常要简单得多。
详细说明:
答
这是你问的第一件事就是一个例子吗?
relation_list = list(ModelA.objects.filter(id__gt=100))
obj_query = ModelB.objects.filter(a_relation__in=relation_list)
这将是一个“IN”命令,因为你第一次用它强制转换为list
,然后在你的第二个查询使用它评估relation_list
。
如果您完全相同,Django只会进行一个查询,并为您执行SQL优化。所以它应该更有效率。
如果您对引擎盖下正在发生的事情感到好奇,您随时都可以看到您将执行的SQL命令obj_query.query
。
希望能回答这个问题,如果不是的话,很抱歉。
可以请你发布你的实际Django过滤器查询吗? – efkin