Django:select_related()和内存使用情况

时间:2012-01-05 15:54:58

标签: django memory django-select-related

我正在研究API,我有一个问题。我正在研究select_related()的用法,以便为自己保存一些数据库查询,事实上,它确实有助于减少执行的数据库查询量,以及大型和更复杂查询的费用。

我的问题是,使用select_related()会导致heasvier内存使用吗?运行一些实验我注意到确实是这种情况,但我想知道为什么。无论我是否使用select_related(),响应都将包含完全相同的数据,那么为什么使用select_related()会导致使用更多内存?

是否因为缓存?也许使用单独的数据对象来缓存相同的模型实例?我不知道还有什么想法。

提前致谢。

1 个答案:

答案 0 :(得分:8)

这是一个权衡。将查询发送到数据库,数据库准备结果,然后将结果发送回来需要时间。 select_related的工作原理是,此过程中最昂贵的部分是请求和响应周期,而不是实际查询,因此它允许您将原本不同的查询组合成一个,因此只有一个请求和反应而不是多重。

但是,如果您的数据库服务器功率不足(RAM不足,处理能力不足等),那么较大的查询实际上最终会花费比请求和响应周期更长的时间。如果是这种情况,您可能需要升级服务器,而不是不使用select_related

经验法则是,如果您需要相关数据,请使用select_related。如果它实际上不是更快,那么这就是您需要优化数据库的标志。

更新(添加更多说明)

查询数据库实际上涉及多个步骤:

  1. 应用程序生成查询(可忽略不计)
  2. 将查询发送到数据库服务器(毫秒到秒)
  3. 数据库处理查询(毫秒到秒)
  4. 将查询结果发送回应用程序(毫秒到秒)
  5. 在经过良好调整的环境中(足够的服务器资源,快速连接),整个过程只需几毫秒即可完成。但是,步骤2和4仍然通常比步骤3花费更多时间。这就是为什么发送比简单多个查询更复杂的查询更有意义:瓶颈通常是传输层而不是处理。

    然而,在具有大型和复杂表的功率不足的机器上,数据不佳的数据库可能需要很长时间才能运行查询,从而成为瓶颈。这最终会抵消从发送一个复杂查询而不是多个简单查询所获得的时间减少,即数据库对更简单的查询响应更快,整个过程将花费更少的净时间。

    然而,如果是这种情况,正确的响应是修复数据库端:优化数据库及其配置,添加更多服务器资源等,而不是恢复发送多个简单查询。