【发布时间】:2011-07-03 15:07:56
【问题描述】:
使用 ruby 和新的 Activerecord 在列中查找具有重复值的记录的最佳方法是什么?
【问题讨论】:
-
只有 1 列或多于 1 列的重复值?是/是这些字符串/整数/文本字段吗?
-
只有 1 列 - 字符串。
标签: ruby activerecord arel
使用 ruby 和新的 Activerecord 在列中查找具有重复值的记录的最佳方法是什么?
【问题讨论】:
标签: ruby activerecord arel
将@TuteC 翻译成 ActiveRecord:
sql = 'SELECT id,
COUNT(id) as quantity
FROM types
GROUP BY name
HAVING quantity > 1'
#=>
Type.select("id, count(id) as quantity")
.group(:name)
.having("quantity > 1")
【讨论】:
PGError: ERROR: column "quantity" does not exist
Type.select("id, count(id) as quantity").group(:name).having("count(id) > 1")
以下是我使用 AREL 助手解决它的方法,没有自定义 SQL:
Person.select("COUNT(last_name) as total, last_name")
.group(:last_name)
.having("COUNT(last_name) > 1")
.order(:last_name)
.map{|p| {p.last_name => p.total} }
真的,这只是编写 SQL 的一种更好的方式。这会找到所有具有重复 last_name 值的记录,并告诉您有多少个姓氏以及哪些姓氏在一个不错的哈希中。
【讨论】:
我正在用 2016 堆栈(Rails 4.2、Ruby 2.2)解决这个问题,并得到了我想要的:
> Model.select([:thing]).group(:thing).having("count(thing) > 1").all.size
=> {"name1"=>5, "name2"=>4, "name3"=>3, "name4"=>2, "name5"=>2}
【讨论】:
使用自定义 SQL,这会发现 types 与 name 的值相同:
sql = 'SELECT id, COUNT(id) as quantity FROM types
GROUP BY name HAVING quantity > 1'
repeated = ActiveRecord::Base.connection.execute(sql)
【讨论】:
在 Rails 2.x 中,select 是 AR 类的私有方法。只需使用 find():
klass.find(:all,
:select => "id, count(the_col) as num",
:conditions => ["extra conditions here"],
:group => 'the_col',
:having => "num > 1")
【讨论】:
这是一个扩展其他答案的解决方案,以显示如何查找和遍历按重复字段分组的记录:
duplicate_values = Model.group(:field).having(Model.arel_table[:field].count.gt(1)).count.keys
Model.where(field: duplicate_values).group_by(&:field).each do |value, records|
puts "The records with ids #{records.map(&:id).to_sentence} have field set to #{value}"
end
这似乎很遗憾,这必须通过两个查询来完成,但this answer 确认了这种方法。
【讨论】: