我正在嘗試分頁洗牌ActiveRecord查詢。這樣做使用雷寶石的語法是:分頁洗牌ActiveRecord查詢
@users = Kaminari.paginate_array(User.all.shuffle).page(params[:page]).per(20)
的問題與此是User.all
重新洗牌每個分頁請求,導致被稱爲重複的記錄。有什麼辦法可以防止這種重複?
我正在嘗試分頁洗牌ActiveRecord查詢。這樣做使用雷寶石的語法是:分頁洗牌ActiveRecord查詢
@users = Kaminari.paginate_array(User.all.shuffle).page(params[:page]).per(20)
的問題與此是User.all
重新洗牌每個分頁請求,導致被稱爲重複的記錄。有什麼辦法可以防止這種重複?
您需要將種子蘭特查詢之間
params[:seed] ||= Random.new_seed
srand params[:seed].to_i
@users = Kaminari.paginate_array(User.all.shuffle).page(params[:page]).per(20)
並在視圖中添加PARAMS [:種子]所有雷鏈接
頁作爲KandadaBoggu上面所指出的,檢索所有User
的當您僅需要20時,數據庫中的記錄效率低下。我建議使用MySQL's RAND()
function執行之前從數據庫返回的。您仍然可以將種子值傳遞至RAND()
以確保每次會話只發生一次混洗。
例如:
class User < ActiveRecord::Base
def self.randomized(seed = nil)
seed = seed.to_i rescue 0
order("RAND(#{seed})")
end
end
class UsersController < ApplicationController
before_filter :set_random_seed
def index
@users = User.randomized(session[:seed]).page(params[:page]).per(20)
end
private
def set_random_seed
session[:seed] ||= Random.new_seed
end
end
我沒有MySQL安裝要測試的,但這應該執行比你原來的代碼更好。
你也可以這樣做:
class UsersController < ApplicationController
USERS_SEED = 1000 # Or any another not-so-big number
def set_random_seed
session[:seed] ||= Random.rand(USERS_SEED)
end
end
因爲Random.new_seed
,如果你的數據不是很大會產生很可能是相同的結果。
調用'User.all'會導致服務器顯着減速。即使你只有100個用戶,你也會支付在每次請求中將所有用戶帶到ruby內存空間的不必要花費。 – 2012-04-09 02:40:21