订购玩家关于其关联模型的SUM

Fre*_*III 5 group-by sum associations has-many ruby-on-rails-3

我有一个6500的数据库,players每个玩家平均有15个游戏results.

用例

我想生成一个玩家列表,按照他们的奖金总和(结果表中的一个字段)排序.我更喜欢这个在某种范围内,所以我也可以过滤播放器所在国家/地区的列表等.

性能

我看到过提及cache_counter性能领域的帖子.在我的情况下,我有成千上万的结果记录(75.000+)所以我不希望每次有人访问生成的列表时都进行计算.

解决这个问题的最佳模式是什么?我该如何实现它?

楷模

class Player < ActiveRecord::Base
  has_many :results
end

class Result < ActiveRecord::Base
  belongs_to :player
end
Run Code Online (Sandbox Code Playgroud)

架构

  create_table "players", :force => true do |t|
    t.string   "name"
    t.string   "nationality"
  end

  create_table "results", :force => true do |t|
    t.integer  "player_id"
    t.date     "event_date"
    t.integer  "place"
    t.integer  "prize"
  end
Run Code Online (Sandbox Code Playgroud)

更新

我想要完成的是达到我可以使用的程度:

@players = Player.order_by_prize
Run Code Online (Sandbox Code Playgroud)

@players = Player.filter_by_country('USA').order_by_prize('desc')
Run Code Online (Sandbox Code Playgroud)

Sal*_*lil 10

你应该可以使用这样的东西:

class Player
 scope :order_by_prize, joins(:results).select('name, sum(results.prize) as total_prize').order('total_prize desc')  
Run Code Online (Sandbox Code Playgroud)

有关详细信息,请参阅rails api - 活动记录查询.

  • 我不得不对你的建议做一些调整,现在它准确地按照他们的奖金总和来命令:`范围:order_by_prize,加入(:结果).select('players.id,players.name,sum(results.prize) as total_prize').group('players.id').order('total_prize desc')`.但是,结果只显示`player.id`和`player.name`,而不是`total_prize`结果? (4认同)
  • 组('players.id')子句为所有玩家创建单独的总和.没有它,所有玩家的所有奖品都会加在一起. (3认同)