【问题标题】:Using Enumerable to make standard iterators available to modify iterators使用 Enumerable 使标准迭代器可用于修改迭代器
【发布时间】:2014-11-13 22:12:58
【问题描述】:

尝试使用 Enumerable mixin 使所有标准迭代器在我的名为 NumberArray 的类中可用。由此我尝试使用注入迭代器来获取数组中奇数的平均值。

我的代码是这样的

 class NumberArray
  include Enumerable
  def initialize
    @numbers = Array.new
  end

然后@numbers 数组被填充 1000 个数字

最后我尝试创建自己的注入迭代器来获取奇数值的平均值。

def inject

    puts self.inject{|sum,x| sum = sum + x if sum mod 2 == 1}

    asum
  end

我对 Ruby 很陌生。

【问题讨论】:

    标签: ruby iterator inject


    【解决方案1】:

    使用Enumerable mixin 的类必须有一个each 方法,该方法为每个连续的元素生成。

    由于您的类 NumberArray 由普通数组支持,您可以使用数组的 each 方法:

    class NumberArray
      # ...
      def each
        @numbers.each
      end
    end
    

    至于您的inject 方法,当您调用self.inject 时,它只是再次调用您当前所在的方法。这称为递归,在这种情况下将导致SystemStackError。我也不建议在NumberArray 中重新定义inject 方法,因为它会覆盖injectEnumerable 实现。

    我会使用更具描述性的方法名称,例如 odd_avg

    def odd_avg
      odds = @numbers.select(&:odd?)
      odds.inject(:+).to_f / odds.size
    end
    

    此方法的第一行从@numbers 中获取所有奇数元素,并将其放入odds。下一行首先获取odds 的总和,然后将总和转换为浮点数,然后除以赔率。

    【讨论】:

      【解决方案2】:

      你也可以只继承 Array 并覆盖你想要的方法:

      class NumberArray < Array
        def inject
          odds = select(&:odd?)
          odds.inject(:+).to_f / odds.size
        end
      end
      
      a = NumberArray.new([1,2,3,4,5])
      a.inject # => 3.0
      

      如果这样做有意义是另一回事,但这就是你问的:)

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2011-03-02
        • 2019-08-09
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2022-11-20
        • 1970-01-01
        相关资源
        最近更新 更多