Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/ruby/23.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Ruby 从匹配值(如hashie deeplocate)查找嵌套哈希中的所有键,同时保留祖先层次结构_Ruby_Hash_Tree_Iteration - Fatal编程技术网

Ruby 从匹配值(如hashie deeplocate)查找嵌套哈希中的所有键,同时保留祖先层次结构

Ruby 从匹配值(如hashie deeplocate)查找嵌套哈希中的所有键,同时保留祖先层次结构,ruby,hash,tree,iteration,Ruby,Hash,Tree,Iteration,假设我有一个深度嵌套的散列,例如 data = { key1: 'foo baz', arbitary_key2: { arbitrary_key3: { unknown_key4: "bar baz", unknown_key5: "foo qux" }, key6: "bar qux" }} 有没有办法找到匹配的钥匙,然后只把保留了祖先的钥匙拿回来 > data.deep_select { |key, value| /bar/i.m

假设我有一个深度嵌套的散列,例如

data = {
  key1: 'foo baz',
  arbitary_key2: {
    arbitrary_key3: {
      unknown_key4: "bar baz",
      unknown_key5: "foo qux"
    },
  key6: "bar qux"
}}
有没有办法找到匹配的钥匙,然后只把保留了祖先的钥匙拿回来

> data.deep_select { |key, value| /bar/i.match?(value) }
# => {
  arbitary_key2: {
    arbitrary_key3: {
      unknown_key4: "bar baz"
    }
  },
  key6: "bar qux"
}

Hashie::DeepLocate让我非常接近,但只返回找到的结果的叶子,并且我一路上丢失了父键。如何保留层次结构?

用于在树中查找子级并获取其祖先。

以下递归方法将返回所需的数组

def filter(h,re)
  h.each_with_object({}) do |(k,v),g|
    if v.is_a?(Hash)
      f = filter(v,re)
      g[k] = f unless f.empty?
    else
      g[k] = v if v.match?(re)
    end
  end
end


它似乎不喜欢使用现有的哈希。尝试使用Tree::TreeNode.from_散列({a:{b:{c}})会给出ArgumentError,“无效的子项。必须是nil或hash。”因为传入的散列中的每个值都应该是nil或hash。idk为什么,但他们是这样编码的:/对提交给RubyTree的GH问题的评论:这应该是一个评论,因为这只是一个建议的方法。为了让它成为一个答案,你需要展示如何使用gem来获得期望的结果,最好将它应用到问题中给出的例子中。无耻的插件:使用
iteraptor
可以这样做
map
data.iteraptor.map{|(key,value){bar/i.match?(value)【key,value]:nil}{:arbitary_key2=>{:arbitary_key3=>{:unknown_key4=>“bar baz”},:key6=>“bar qux”}
。您需要显式地将
yield_all:true
参数传递给
map
modified=origing.iteraptor.map(yield_all:true){|,(key,value)|[key,value]if/{{query}/i.match?(String(value))
。没有空数组就无法删除它的原因是:
yield\u all:false
(默认)这意味着您只映射值,在这个分支中,上面的所有内容都是可迭代的。最后一个可迭代对象是空数组,它将被映射。对于它本身:shrug:FWIW,您还可以将其展平并获取回来:
original.aplanar.select{| |,v |/course/i=~v.To|s}.recoger
。但是想要的结果是一个经过过滤的散列,而不是一个密钥数组。非常欢迎,一如既往!自从我退出ruby后我就想你了:)@AlekseiMatiushkin,我不知道你竟然退出ruby。你和Elixer现在是一个项目了吗?西班牙现在是一个可怕的地方。请注意安全。我仍然支持一些gems和我们的合作伙伴ternal ruby的东西,但大多数情况下我都在用长生不老药,我对此很满意。不过,西班牙并不像他们说的那么可怕。世界上最可怕的事情总是人类,所以我要说病毒在这场战斗中没有机会:)谢谢!我一直想尝试并报告回来……工作繁忙,一个非常小的团队的工作重点不断变化。.. (-:
data = {
  key1: 'foo baz',
  arbitary_key2: {
    arbitrary_key3: {
      unknown_key4: "bar baz",
      unknown_key5: "foo qux"
    },
    key6: "bar qux"
  }
}
filter(data, /bar/)
  #=> { :arbitary_key2=>{
  #       :arbitrary_key3=>{ :unknown_key4=>"bar baz" },
  #       :key6=>"bar qux"
  #     }
  #   }