Skip to content

Instantly share code, notes, and snippets.

@jodosha
Created February 4, 2009 18:37
Show Gist options
  • Star 4 You must be signed in to star a gist
  • Fork 2 You must be signed in to fork a gist
  • Save jodosha/58257 to your computer and use it in GitHub Desktop.
Save jodosha/58257 to your computer and use it in GitHub Desktop.
Ruby's Hash deep search
class Hash
def deep_has_key?(key)
self.has_key?(key) || any? {|k, v| v.deep_has_key?(key) if v.is_a? Hash}
end
alias :deep_include? :deep_has_key?
alias :deep_key? :deep_has_key?
alias :deep_member? :deep_has_key?
def deep_has_value?(value)
self.has_value?(value) || any? {|k,v| v.deep_has_value?(value) if v.is_a? Hash}
end
alias :deep_value? :deep_has_value?
end
require 'test/unit'
class HashDeepHasKeyTest < Test::Unit::TestCase
def returns_true_on_first_level_search
assert({:a => 'a'}.deep_has_key?(:a))
end
def returns_false_on_first_level_search
assert_false({:a => 'a'}.deep_has_key?(:b))
end
def returns_true_on_second_level_search
assert({:a => {:b => 'b'}}.deep_has_key?(:b))
end
def returns_false_on_second_level_search
assert_false({:a => {:b => 'b'}}.deep_has_key?(:c))
end
def returns_true_on_second_level_and_last_element_search
assert({:a => {:c => 'c'}, :b =>{:d => 'd'}}.deep_has_key?(:d))
end
def returns_false_on_second_level_and_last_element_search
assert_false({:a => {:c => 'c'}, :b =>{:d => 'd'}}.deep_has_key?(:e))
end
def returns_true_on_third_level_and_last_element_search
assert({:a => {:c => 'c'}, :b =>{:d => {:e => 'e'}}}.deep_has_key?(:e))
end
def returns_true_on_deepest_level
assert({:a => {:b => {:c => {:d => {:e => {:f => {:g => {:h => {:i => {:j => {:k => {:l => 'luca'}}}}}}}}}}}}.deep_has_key?(:l))
end
end
class HashDeepHasValueTest < Test::Unit::TestCase
def returns_true_on_first_level_search
assert({:a => 'a'}.deep_has_value?('a'))
end
def returns_false_on_first_level_search
assert_false({:a => 'a'}.deep_has_value?('b'))
end
def returns_true_on_second_level_search
assert({:a => {:b => 'b'}}.deep_has_value?('b'))
end
def returns_false_on_second_level_search
assert_false({:a => {:b => 'b'}}.deep_has_value?('c'))
end
def returns_true_on_second_level_and_last_element_search
assert({:a => {:c => 'c'}, :b =>{:d => 'd'}}.deep_has_value?('d'))
end
def returns_false_on_second_level_and_last_element_search
assert_false({:a => {:c => 'c'}, :b =>{:d => 'd'}}.deep_has_value?('e'))
end
def returns_true_on_third_level_and_last_element_search
assert({:a => {:c => 'c'}, :b =>{:d => {:e => 'e'}}}.deep_has_value?('e'))
end
def returns_true_on_deepest_level
assert({:a => {:b => {:c => {:d => {:e => {:f => {:g => {:h => {:i => {:j => {:k => {:l => 'luca'}}}}}}}}}}}}.deep_has_value?('luca'))
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment