我有一个评论表和一个帖子表,其中帖子有很多评论,评论属于一个帖子(即表格中有一个post_id)。
如何有效地选择没有评论的最后十个帖子。 如果没有先选择所有帖子并检查每个帖子的0评论数,我似乎无法做到这一点。
提前感谢您的帮助。
-Nathan
答案 0 :(得分:8)
你可以做到
Post.find(:all, :include => :comments, :conditions => "comments.id is null", :limit => 10, :order => "created_at desc")
答案 1 :(得分:3)
您可以向Comment
模型添加counter cache,向Post
模型添加几个named scopes。类似的东西:
class Post < ActiveRecord::Base
has_many :comments
named_scope :recent, :limit => 10, :order => 'created_at DESC'
named_scope :uncommented, :conditions => { :comments_count => 0 }
end
class Comment < ActiveRecord::Base
belongs_to :post, :counter_cache => true
end
如果您使用的是Rails 3,那么命名的范围语法会略有不同:
class Post < ActiveRecord::Base
has_many :comments
scope :recent, limit(10).order('posts.created_at DESC')
scope :uncommented, where(:comments_count => 0)
end
现在,您可以通过将命名范围链接在一起来查找没有任何注释的帖子:
@uncommented = Post.recent.uncommented
如果你想获得所有帖子而没有任何评论(即不仅仅是最近的十篇帖子),那么它将是:
@uncommented = Post.uncommented
- 您可能已经注意到,在Rails 3示例中,我在posts
范围中包含了:recent
表名。这是一个很好的做法,以便在两个表具有相同列名的情况下避免SQL查询中的模糊列名。 This Railscast解释了更多。
答案 2 :(得分:1)
在帖子表中添加comments_count
列,让迁移更新计数器。从现在开始,如果您在关联上提供:counter_cache => true
,Rails将自动更新您的计数器。现在很容易选择最后10个帖子:
Post.find_all_by_comments_count 0, :order => 'created_at DESC', :limit => 10
文档链接:http://rails.rubyonrails.org/classes/ActiveRecord/Associations/ClassMethods.html#M001318
答案 3 :(得分:0)
您必须以某种方式添加条件:
:conditions => '(SELECT count(*) FROM comments WHERE post_id = #{id}) = 0'
我不是SQL方面的专家,所以也许有类似EMPTY关键字的东西。
答案 4 :(得分:0)
您需要的是左外连接:
Post.all :joins => "left outer join comments on posts.id = comments.post_id", :conditions => "comments.id is null", :limit => 10, :order => 'created at desc'
此链接可帮助您了解不同类型的SQL连接:http://www.codinghorror.com/blog/2007/10/a-visual-explanation-of-sql-joins.html
答案 5 :(得分:0)
Post.includes(:comments).where(“comments.id为null”)