Se controlli il contenuto dell'hash, ed è relativamente piccolo, vorrei usare qualcosa di simile in un metodo privato come soluzione generica.
def exclusively_true?(hash, key)
return false unless hash.delete(key) == true
!hash.has_value? true
end
require 'test/unit'
class TestExclusive < Test::Unit::TestCase
def setup
@test_hash = {foo: true, bar: false, hoge: false}
end
def test_exclusive
assert_equal(true, exclusively_true?(@test_hash, :foo))
end
def test_inexclusive
@test_hash[:bar] = true
assert_equal(false, exclusively_true?(@test_hash, :foo))
end
end
require 'benchmark'
h = {foo: true}
999.times {|i| h["a#{i}"] = false}
Benchmark.bmbm(30) do |x|
x.report('exclusively_true') do
1000.times do
exclusively_true?(h, :foo)
end
end
end
benchmark artificiosa: (OS X 10.8.3/3 GHz/8 GB)
ruby -v: ruby 2.0.0p0 (2013-02-24 revision 39474) [x86_64-darwin12.3.0]
Rehearsal ------------------------------------------------------------------
exclusively_true 0.000000 0.000000 0.000000 ( 0.000412)
--------------------------------------------------------- total: 0.000000sec
user system total real
exclusively_true 0.000000 0.000000 0.000000 ( 0.000331)
come se non distruggesse l'hash –
A volte aiuta solo a pensare logicamente che cosa stai cercando di realizzare. Ottimo approccio +1. – squiguy