Come posso verificare se un array di rubini include uno dei valori?
Domanda
Ho due array di rubini e devo vedere se hanno dei valori in comune. Potrei semplicemente passare attraverso ciascuno dei valori in un array e includere? () Dall'altro, ma sono sicuro che c'è un modo migliore. Che cos'è? (Gli array tengono entrambi stringhe.)
Grazie.
Soluzione
Imposta interseca loro:
a1 & a2
Ecco un esempio:
> a1 = [ 'foo', 'bar' ]
> a2 = [ 'bar', 'baz' ]
> a1 & a2
=> ["bar"]
> !(a1 & a2).empty? # Returns true if there are any elements in common
=> true
Altri suggerimenti
Qualche valore in comune? È possibile utilizzare l'operatore di intersezione: &
[ 1, 1, 3, 5 ] & [ 1, 2, 3 ] #=> [ 1, 3 ]
Se stai cercando un incrocio completo (con duplicati) il problema è più complesso, c'è già un overflow dello stack qui: Come restituire un incrocio di array di Ruby con elementi duplicati? (problema con bigrams in coefficiente di dadi)
O un rapido frammento che definisce "real_intersection" e convalida il seguente test
class ArrayIntersectionTests < Test::Unit::TestCase
def test_real_array_intersection
assert_equal [2], [2, 2, 2, 3, 7, 13, 49] & [2, 2, 2, 5, 11, 107]
assert_equal [2, 2, 2], [2, 2, 2, 3, 7, 13, 49].real_intersection([2, 2, 2, 5, 11, 107])
assert_equal ['a', 'c'], ['a', 'b', 'a', 'c'] & ['a', 'c', 'a', 'd']
assert_equal ['a', 'a', 'c'], ['a', 'b', 'a', 'c'].real_intersection(['a', 'c', 'a', 'd'])
end
end
L'uso dell'incrocio sembra bello, ma è inefficiente. Userei "qualcuno?" Sul primo array (in modo che l'iterazione si fermi quando uno degli elementi si trova nel secondo array). Inoltre, l'utilizzo di un set sul secondo array farà rapidamente controlli di abbonamento. cioè:
a = [:a, :b, :c, :d]
b = Set.new([:c, :d, :e, :f])
c = [:a, :b, :g, :h]
# Do a and b have at least a common value?
a.any? {|item| b.include? item}
# true
# Do c and b have at least a common value?
c.any? {|item| b.include? item}
#false
Prova questo
a1 = [ 'foo', 'bar' ]
a2 = [ 'bar', 'baz' ]
a1-a2 != a1
true