通过优化Django中的_sets来减少查询

时间:2012-01-10 20:19:44

标签: python django

以下结果为4 db命中。从第3行和第3行开始4只是过滤我在第2行抓到的东西,我需要更改什么才能再次点击db?

page = get_object_or_404(Page, url__iexact = page_url)
installed_modules = page.module_set.all()
navigation_links = installed_modules.filter(module_type=ModuleTypeCode.MODAL)
module_map = dict([(m.module_static_object.key, m) for m in installed_modules])

2 个答案:

答案 0 :(得分:4)

Django querysets are lazy,因此以下行未命中数据库:

installed_modules = page.module_set.all()

在迭代此行中的查询集之前,不会执行查询:

module_map = dict([(m.module_static_object.key, m) for m in installed_modules])

所以你发布的代码看起来只有3个数据库查询命中,而不是4.

由于您已从数据库中获取所有模块,因此您可以使用列表推导而不是其他查询来过滤导航链接:

navigation_links = [m for m in installed_modules if m.module_type == ModuleTypeCode.MODAL]

你必须做一些基准测试,看看这是否有所改善。看起来对我来说可能是不成熟的优化。

您可能正在为获取module_static_object.key的每个模块执行一次数据库查询。在这种情况下,您可以使用select_related

答案 1 :(得分:1)

这是过早优化的情况。对页面加载的4个DB查询也不错。我们的想法是尽可能少地使用查询,但是在每种情况下你永远不会将它降为1。你所拥有的代码在不必要地创建查询方面看起来并不像现在这样,所以它很可能已经像你能够做到的那样进行了优化。