rails - ruby slice
Cómo contar duplicados en Ruby Arrays (13)
¿Cómo se cuentan los duplicados en una matriz de rubíes?
Por ejemplo, si mi matriz tiene tres a, ¿cómo podría contar eso?
¿Qué tal un grep?
arr = [1, 2, "Thanks", "You''re welcome", "Thanks", "You''re welcome", "Thanks", "You''re welcome"]
arr.grep(''Thanks'').size # => 3
Dado:
arr = [ 1, 2, 3, 2, 4, 5, 3]
Mi forma favorita de contar elementos es:
counts = arr.group_by{|i| i}.map{|k,v| [k, v.count] }
# => [[1, 1], [2, 2], [3, 2], [4, 1], [5, 1]]
Si necesita un hash en lugar de una matriz:
Hash[*counts.flatten]
# => {1=>1, 2=>2, 3=>2, 4=>1, 5=>1}
Es fácil:
words = ["aa","bb","cc","bb","bb","cc"]
Una solución simple de una línea es:
words.each_with_object(Hash.new(0)) { |word,counts| counts[word] += 1 }
Esto funciona para mi.
¡¡Gracias!!
Esto producirá los elementos duplicados como un hash con el número de ocurrencias para cada elemento duplicado. Deje que el código hable:
#!/usr/bin/env ruby
class Array
# monkey-patched version
def dup_hash
inject(Hash.new(0)) { |h,e| h[e] += 1; h }.select {
|k,v| v > 1 }.inject({}) { |r, e| r[e.first] = e.last; r }
end
end
# unmonkeey''d
def dup_hash(ary)
ary.inject(Hash.new(0)) { |h,e| h[e] += 1; h }.select {
|_k,v| v > 1 }.inject({}) { |r, e| r[e.first] = e.last; r }
end
p dup_hash([1, 2, "a", "a", 4, "a", 2, 1])
# {"a"=>3, 1=>2, 2=>2}
p [1, 2, "Thanks", "You''re welcome", "Thanks",
"You''re welcome", "Thanks", "You''re welcome"].dup_hash
# {"You''re welcome"=>3, "Thanks"=>3}
He usado reduce
/ inject
para esto en el pasado, como el siguiente
array = [1,5,4,3,1,5,6,8,8,8,9]
array.reduce (Hash.new(0)) {|counts, el| counts[el]+=1; counts}
produce
=> {1=>2, 5=>2, 4=>1, 3=>1, 6=>1, 8=>3, 9=>1}
Mejorando la respuesta de @ Kim:
arr = [1, 2, "a", "a", 4, "a", 2, 1]
Hash.new(0).tap { |h| arr.each { |v| h[v] += 1 } }
# => {1=>2, 2=>2, "a"=>3, 4=>1}
No creo que haya un método incorporado. Si todo lo que necesita es el recuento total de duplicados, podría tomar a.length - a.uniq.length. Si busca el conteo de un solo elemento en particular, intente
a.select {|e| e == my_element}.length
a.select {|e| e == my_element}.length
.
Otra forma de contar los lotes duplicados es:
arr= [2,2,3,3,2,4,2]
arr.group_by{|x| x}.map{|k,v| [k,v.count] }
resultado es
[[2, 4], [3, 2], [4, 1]]
Otra versión de un hash con una clave para cada elemento en su matriz y valor para el recuento de cada elemento
a = [ 1, 2, 3, 3, 4, 3]
h = Hash.new(0)
a.each { | v | h.store(v, h[v]+1) }
# h = { 3=>3, 2=>1, 1=>1, 4=>1 }
Para contar instancias de un solo elemento, use inyectar
array.inject(0){|count,elem| elem == value ? count+1 : count}
Sencillo.
arr = [2,3,4,3,2,67,2]
repeats = arr.length - arr.uniq.length
puts repeats
requiere 1.8.7+ para group_by
ary = %w{a b c d a e f g a h i b}
ary.group_by{|elem| elem}.select{|key,val| val.length > 1}.map{|key,val| key}
# => ["a", "b"]
con 1.9+ esto se puede simplificar levemente porque Hash # select devolverá un hash.
ary.group_by{|elem| elem}.select{|key,val| val.length > 1}.keys
# => ["a", "b"]
arr = %w( a b c d c b a )
# => ["a", "b", "c", "d", "c", "b", "a"]
arr.count(''a'')
# => 2