【问题标题】:How does enum#with_object differ from enum#each_with_object?enum#with_object 与 enum#each_with_object 有何不同?
【发布时间】:2013-02-03 11:18:15
【问题描述】:

文档说:

enum#each_with_object :-

使用任意对象 obj 迭代每个元素的给定块,并返回 obj

enum#with_object:-

使用任意对象 obj 迭代每个元素的给定块,并返回 obj

但是当我在这两种结构上尝试以下操作时,一个给了我预期的输出,但其他的却没有。所以我怀疑这两种结构之间存在差异。

使用each_with_object

%w(foo bar).each_with_object({}) { |str, hsh| hsh[str] = str.upcase }
=> {"foo"=>"FOO", "bar"=>"BAR"}

成功了!

使用with_object

%w(foo bar).with_object({}) { |str, hsh| hsh[str] = str.upcase }
 => NoMethodError: undefined method `with_object' for ["foo", "bar"]:Array
    from (irb):1
    from C:/Ruby193/bin/irb:12:in `<main>'

这里失败了!

那么这两种方法有什么区别呢?

【问题讨论】:

    标签: ruby ruby-1.9


    【解决方案1】:

    each 返回一个 Enumerator 对象。

    %w(foo bar).each.class
    => Enumerator
    

    因此,对于第一种情况,数组将首先转换为Enumerator,然后在with_object 上工作。

    如果您希望第二种情况有效,则必须将数组转换为 Enumerator。您可以使用.to_enum.each.map 来转换数组。

    %w(foo bar).map.with_object({}) { |str, hsh| hsh[str] = str.upcase }
    => {"foo"=>"FOO", "bar"=>"BAR"}
    

    更多详情:Enumerator

    【讨论】:

    • @DoLoveSky 不是这样:each.with_objecteach_with_object 是相同数量的字符(如果算上 shift 键,前者会少一个按键)。
    • @DoLoveSky 不,我没有,因为它根本不保存击键。
    【解决方案2】:

    with object 仅适用于枚举器,这意味着您必须将其链接到返回一个的东西上。例如。

    %w(foo bar).each.with_object({}) { |str, h| h[str] = str.upcase }
    
    %w(foo bar).detect.with_object(obj) { ... }
    

    所以,如果你不给它一个块,你可以在任何返回枚举数的东西上调用with_object(例如mapreducedetectfind_all...)。这包括混入Enumerable 的任何内容。

    each_with_object本质上是each.with_object的别名。

    【讨论】:

    • 您能否详细说明%w(foo bar).detect.with_object(obj) { ... } 构造?
    • 已添加。这只是返回枚举器的其他示例,不是each
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-02-24
    • 1970-01-01
    • 2017-02-08
    • 2013-08-19
    相关资源
    最近更新 更多