【问题标题】:Ruby Array find_first object?Ruby Array find_first 对象?
【发布时间】:2011-01-23 18:45:39
【问题描述】:

我是否遗漏了 Array 文档中的某些内容?我有一个数组,其中最多包含一个满足某个标准的对象。我想有效地找到那个对象。我从文档中得到的最好的想法是:

candidates = my_array.select { |e| e.satisfies_condition? }
found_it = candidates.first if !candidates.empty?

但我不满意有两个原因:

  1. select 让我遍历了整个数组,尽管我们本可以在第一次命中后放弃。
  2. 我需要一行代码(带有条件)来扁平化候选人。

这两种操作都是浪费的,因为预先知道有 0 或 1 个令人满意的对象。

我想要的是这样的:

array.find_first(block)

它返回 nil 或该块计算为真的第一个对象,结束对该对象的遍历。

我必须自己写吗? Array 中所有其他很棒的方法让我觉得它就在那里,我只是没有看到它。

【问题讨论】:

    标签: ruby arrays performance find


    【解决方案1】:

    要么我不明白你的问题,要么Enumerable#find 就是你要找的东西。

    【讨论】:

    • 没问题,我也经常觉得烦人的是 ruby​​ 文档没有列出所有继承或包含的类和模块的方法。
    • 更多信息:[1,2,3,5,2].find { |n| puts n; n == 2 } 一旦找到匹配的第一个元素,迭代就会停止。
    【解决方案2】:

    如果你想在 block 返回 true 的地方返回第一个值,请使用数组 detect 方法

    [1,2,3,11,34].detect(&:even?) #=> 2
    
    OR
    
    [1,2,3,11,34].detect{|i| i.even?} #=> 2
    

    如果您想返回 block 返回 true 的所有值,请使用 select

    [1,2,3,11,34].select(&:even?)  #=> [2, 34]
    

    【讨论】:

    【解决方案3】:

    您需要对象本身还是只需要知道是否有 对象满足。 如果是前者,那么是:使用 find:

    found_object = my_array.find { |e| e.satisfies_condition? }
    

    否则你可以使用any?

    found_it = my_array.any?  { |e| e.satisfies_condition? }
    

    当后者找到满足条件的对象时,它将以“真”的形式保释。 前者会做同样的事情,但会返回对象。

    【讨论】:

      【解决方案4】:

      猜你只是错过了文档中的 find 方法:

      my_array.find {|e| e.satisfies_condition? }
      

      【讨论】:

      • 或者如果你喜欢打码打高尔夫球,my_array.find(&:satisfies_condition?)
      猜你喜欢
      • 2013-03-09
      • 1970-01-01
      • 1970-01-01
      • 2018-03-18
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-05-21
      相关资源
      最近更新 更多