所以 hashie 有一个 deep_find_all 方法,可以用来查找嵌套散列中的所有键,但是有没有办法进行深度删除或深度查找,以一种可以删除键的方式返回键。
我看到在哪里可以将哈希转换为 mashie 并进行删除,但它似乎并没有超出顶层。
我试图从 JSON 中删除所有包含时间戳的键,以便我可以比较来自两个不同主机的结果。我已经实现了一种方法来做到这一点,但它似乎有点笨拙,深度删除只是门票。
谢谢克雷格
所以 hashie 有一个 deep_find_all 方法,可以用来查找嵌套散列中的所有键,但是有没有办法进行深度删除或深度查找,以一种可以删除键的方式返回键。
我看到在哪里可以将哈希转换为 mashie 并进行删除,但它似乎并没有超出顶层。
我试图从 JSON 中删除所有包含时间戳的键,以便我可以比较来自两个不同主机的结果。我已经实现了一种方法来做到这一点,但它似乎有点笨拙,深度删除只是门票。
谢谢克雷格
您可以制作一个通用的 ruby 方法:
def hash_recurse(hash, &blk)
hash.each do |key, val|
blk.call(hash, key, val)
if val.is_a?(Hash)
hash_recurse(val, &blk)
end
end
end
然后您可以传递任何块,包括要删除的块:
hash = {
a: {
timestamp: 123,
key: "val1"
},
b: {
timestamp: 456,
foo: "val2"
}
}
hash_recurse(hash) do |_hash, key, val|
_hash.delete(key) if key == :timestamp
end
puts hash
# => {:a=>{:key=>"val1"}, :b=>{:foo=>"val2"}}
这与深度优先搜索本质上是一样的。例如,如果您想提取哈希中所有键的“路径”及其子哈希,您可以修改它以保留当前路径的记录:
def hash_recurse(hash, path=[], &blk)
hash.each do |key, val|
new_path = path + [key]
blk.call(hash, key, val, new_path)
if val.is_a?(Hash)
hash_recurse(val, new_path, &blk)
end
end
end
并像这样获取路径:
paths = []
hash_recurse(hash) do |_hash, key, val, path|
paths << path
end
paths.each { |path| puts path.join(",") }
# =>
# a
# a,timestamp
# a,key
# b
# b,timestamp
# b,foo