论坛首页 编程语言技术论坛

Ruby for Rails 一书中的问题: 关于 sql

浏览 3688 次
精华帖 (0) :: 良好帖 (0) :: 新手帖 (0) :: 隐藏帖 (0)
作者 正文
   发表时间:2006-09-15  
我正在翻译 Ruby for Rails 一书, 目前已经翻译到16章, 翻译过程中发现了一些问题, 希望论坛里的朋友可以帮忙看一下。

原文见 p.401
def editions
    works.map {|work| work.editions }.flatten.uniq
end


This method starts by unconditionally gathering all the works by this composer, which it does by calling works. At this point, ActiveRecord is finished; the one and only database query required here returns all the works for this composer. What remains is pure Ruby: harvesting the editions of the works (courtesy of map) and massaging the resulting array-of-arrays of editions with flatten and uniq. Each of these operations creates a new array—potentially a large one, if we’re dealing with a well-stocked music store.


请看红色标出部分。我认为这段代码中不只一个 database query.
works 是一个 database query , editions 也是一个 database query。

请帮忙看一下,谢谢。
   发表时间:2006-09-15  
这里有n+1个查询呢
0 请登录后投票
   发表时间:2006-09-15  
是啊. 在java orm里面这个问题折腾了很多年了。不过足够牛比的话一条 sql语句也能搞定,记得在ibatis里面这样的东西是要特别定制的,也许activerecord足够强悍?
0 请登录后投票
   发表时间:2006-09-15  
charon 写道
是啊. 在java orm里面这个问题折腾了很多年了。不过足够牛比的话一条 sql语句也能搞定,记得在ibatis里面这样的东西是要特别定制的,也许activerecord足够强悍?



同样的功能确实可以指用一条 sql 完成,作者在书中也给出了该 sql。
但就这条Ruby 语句来说,我认为自动性能优化是不可能的。请看代码:
  works.map {|work| work.editions }
对于works.map 的 map  调用来说, {|work| work.editions }只是一个代码块,这个代码块的内容 map 是看不见的, 它可以是任意内容。所以, map即使被 ActiveRecord 定制, 也不可能判断出块中是 editions 调用并据此进行优化。

而能看到整个语句的是 Ruby 解释器, 而不是 Rails 解释器或 ActiveRecord 解释器一类的东西(没有这种东西)。也就是说,能够获得所有的信息并据此做出优化的只能是 Ruby 解释器, 而 Ruby 解释器显然不可能做这个工作。

因此,我认为, 这里的 SQL 查询不可能被合并。
0 请登录后投票
   发表时间:2006-09-15  
这个在console里简单试一下就知道肯定是n+1条查询,不会自动eager loading的。除非用新的:include选项。
0 请登录后投票
   发表时间:2006-09-15  
cookoo 写道
这个在console里简单试一下就知道肯定是n+1条查询,不会自动eager loading的。除非用新的:include选项。

是这样的。
0 请登录后投票
论坛首页 编程语言技术版

跳转论坛:
Global site tag (gtag.js) - Google Analytics