我有一个名为note
的模型。我目前得到这样的笔记:
current_user.notes.order('date DESC, created_at DESC').limit(10).reverse!
我现在需要做以下事情: 取一个note_id参数,然后返回10个音符:参数中的一个和第一个附近的9个其他音符。
理想情况下,根据上面第一行中的顺序,其他9个音符将在主音符之前分配为5,在之后4之后(或在之后的4之前和之后为5)。
示例:
note note note note primary_note note note note note note
有时候这是不可能的。例如,如果primary_note是用户的第二个音符,它应该返回:
note primary_note note note note note note note note note
或者如果它是最新的音符,并且用户总共只有3个音符,则应该返回:
note note primary_note
我该怎么做?我正在使用ruby 1.9.2& Rails 3.0.1
答案 0 :(得分:4)
我认为没有办法通过单一查询获得这些笔记 - 您至少需要两个。从我对SQL(对某种程度有限)的理解,你必须做到的唯一方法是:
primary_note
primary_note
类似的东西(警告:未经测试的代码)
class Note < ActiveRecord::Base
# on rails 3 I prefer class methods to named scopes.
# they are equally "chainable" and have simpler syntax
def self.notes_before(date, limit=4)
self.where(['date >= ?', date]).order("date DESC, created_at DESC").limit(limit)
end
def self.notes_after(date, limit=4)
self.where(['date <= ?', date]).order("created_at ASC, date ASC").limit(limit)
end
# Instance method
def notes_around(limit=4)
(Note.notes_before(self.date, limit) << self) + Note.notes_after(self.date, limit)
end
end
用法:
n = Note.new(:date => Date.yesterday)
n.notes_around # returns the 9 notes around n, plus n
n.notes_around(40) # returns 81 notes
# in addition:
Note.notes_before(Date.today, 40) # last 40 notes
Note.notes_after(Date.today, 10).where(:color => 'blue') # chainable
但我想不出一个“可连接的类方法”。也许我不太了解SQL。
理想情况下,其他9个笔记将是 在主要说明之前分配为5 和之后的4(或之前的4和之后的5), 基于第一个排序 上面的行
我不明白你如何确定在这种情况下你需要“4”或“5”。所以我假设你知道这一点。
答案 1 :(得分:2)
您可以在查询中使用range condition
class Note
scope :around_note_id, lambda { |id| where(:id => range_for_search(id) }
def self.range_for_search(id)
# your logic here, i.e.
# (id-1)..(id+1)
end
end
> Note.around_note_id(3)