迭代包含哈希和/或数组的嵌套哈希。

8
我有一个哈希表,我想提取它的键和值。该哈希表中包含嵌套的哈希表和/或哈希表数组。
在查看了本网站和一些示例后,我得到了键和值。但是,在提取哈希表数组时遇到了困难。
例如:
{
  :key1 => 'value1',
  :key2 => 'value2',
  :key3 => {
    :key4 => [{:key4_1 => 'value4_1', :key4_2 => 'value4_2'}],
    :key5 => 'value5'
  },
  :key6 => {
    :key7 => [1,2,3],
    :key8 => {
      :key9 => 'value9'
    }
  }
}

目前我有以下代码,来自如何在Ruby中循环遍历哈希表在Ruby中迭代深度嵌套的哈希表

def ihash(h)
  h.each_pair do |k,v|
    if v.is_a?(Hash) || v.is_a?(Array)
      puts "key: #{k} recursing..."
      ihash(v)
    else
      # MODIFY HERE! Look for what you want to find in the hash here
      puts "key: #{k} value: #{v}"
    end
  end
end

但在 v.is_hash?(Array)v.is_a?(Array) 处失败。

我有什么遗漏吗?


1
你期望的输出是什么? - Arup Rakshit
3个回答

21

不太清楚您需要什么,但是ArrayHash都实现了each方法(在Hash的情况下,它是each_pair的别名)。

所以,要获得与您的方法产生相同的输出,您可以像这样实现:

def iterate(h)
  h.each do |k,v|
    # If v is nil, an array is being iterated and the value is k. 
    # If v is not nil, a hash is being iterated and the value is v.
    # 
    value = v || k

    if value.is_a?(Hash) || value.is_a?(Array)
      puts "evaluating: #{value} recursively..."
      iterate(value)
    else
      # MODIFY HERE! Look for what you want to find in the hash here
      # if v is nil, just display the array value
      puts v ? "key: #{k} value: #{v}" : "array value #{k}"
    end
  end
end

1
如果v是一个数组或哈希表,您正在调用ihash(v)。对于数组,each_pair方法调用将失败。

0
你可以跳过递归,使用这样的方式:
a = {}
a[0] = { first: "first" }
a[1] = [{ second: "second_1" }, { second: "second_2" }]

a.each_pair do |k1, v1|
  puts "======== key: #{k1}, value: ========"

  if v1.class == Hash
    v1.each_pair do |k2, v2|
      puts "key_2: #{k2}, value: #{v2}"
    end
  else
    v1.each do |h|
      h.each_pair do |k2, v2|
        puts "hash #{v1.index(h)} => key_2: #{k2}, value: #{v2}"
      end
    end
  end
end

输出:

======== key: 0, value: ========
key_2: first, value: first
======== key: 1, value: ========
hash 0 => key_2: second, value: second_1
hash 1 => key_2: second, value: second_2

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接