用模型方法查询?

Kom*_*mbo 6 ruby-on-rails ruby-on-rails-3

我在仅对活动对象执行查询时遇到问题.我在数据库中没有活动列,相反,在模型游戏中,我有以下方法:

def complete?
  self.winner ? true : false
end
Run Code Online (Sandbox Code Playgroud)

这样,如果一个游戏有一个胜利者,#complete?将返回true.我想查询所有会为此方法返回false的游戏,有没有办法用ActiveRecord执行此操作?现在在我的控制器中我只是打电话@games = Game.all,然后在我的部分渲染游戏中:

<% unless game.complete? %>
yada yada
<% end %>
Run Code Online (Sandbox Code Playgroud)

这似乎有点hacky,如果我想显示"已完成"的游戏,则需要我写一个不同的部分.无论如何,我想知道控制器中是否有一种方法只能分配从模型方法返回true/false的对象?

MrD*_*anA 8

快速简便的类方法怎么样?

class Game < ActiveRecord::Base
    def self.completed_games
        games = []
        Game.all.each { |game| games << game if game.complete? }
        return games
    end
end
Run Code Online (Sandbox Code Playgroud)

然后打电话Game.completed_games.您也可以为不完整的游戏制作一个.您也可以将该方法设为一行,但我将其分解,以便您可以确切地看到正在发生的事情.

  • @snowangel在这个确切的例子中,是的,你是对的.在我写这篇文章的时候,我对Rails还是比较新的,我认为我还没有真正理解范围.但是,从更广泛的意义上讲,如果所讨论的方法更复杂并且无法用SQL编写,那么这种方法仍然可行. (3认同)

mu *_*ort 7

既然winner是属性Game,为什么不查询呢?你只需要这个:

completed  = Game.where('winner is not null')
incomplete = Game.where('winner is null')
Run Code Online (Sandbox Code Playgroud)

如果您愿意,也可以将它们作为范围:

class Game < ActiveRecord::Base
    scope :finished,   where('winner is not null')
    scope :unfinished, where('winner is     null')
    #...
end
Run Code Online (Sandbox Code Playgroud)

然后你可以在数据库出来之前添加进一步的过滤或排序.

让数据库完成工作,他们擅长搜索和投放数据.无论何时将整个表从数据库中拉出来进行客户端处理,您都应该再次考虑,因为您几乎肯定会犯错误.