Django通过模型对象列表过滤

1 投票
2 回答
2858 浏览
提问于 2025-04-18 11:44

我正在尝试通过检查某个对象是否在一组对象的列表中来过滤查询集。

employee_list = [<Employee: A>, <Employee: B>, <Employee: C>]
qs = Employee.objects.filter(id__in=employee_list, [other_filters])

运行上面的代码后,qs变成了一个空列表。我在想我可以创建一个新的列表,比如:

employee_ids = [emp.id for emp in employee_list]
qs = Employee.objects.filter(id__in=employee_ids, [other_filters])

我还没有对这种方法进行性能测试,但我想性能可能会受到影响。或者,我可以在之后交叉比较这些列表,比如:

qs = Employee.objects.filter([other_filters])
filtered_qs = [emp for emp in employee_lids if emp in qs]

不过,我觉得这样做性能损失可能会更大。

有没有更好或更快的方法来实现这个?谢谢。

2 个回答

2

一个简单的经验法则是尽量在SQL中进行过滤,所以我会选择

qs = Employee.objects.filter(id__in=[emp.id for emp in employee_list], [other_filters])

不过我没有性能测试的数据来支持这个说法。

1

正如Martol1ni提到的,尽量在SQL层面进行过滤,这样会更高效,所以我觉得你的方法确实会越来越慢,但还有另一个问题...

根据Django的文档:https://docs.djangoproject.com/en/dev/ref/models/querysets/,我认为你的id__in应该是一个整数ID的列表,而不是模型的列表。

编辑:哦,我明白了,他在他的回答中提到了这一点,但在你的问题中并没有明确指出这是错误的。

编辑2:不过,是的,如果你想确定的话,真正重要的是实际的性能,这可以通过django-debug-toolbar来检查。不过我觉得真正的问题是你对id__in的误用,这让你不得不寻找更复杂的方法来实现你想要的功能。

撰写回答