带分区和with_index的Ruby Split数组

时间:2017-11-23 09:14:40

标签: arrays ruby enumerable enumerator

你能解释一下这种结构的红宝石行为的逻辑或算法:

arr = [1,2,3,4,5]
arr.partition.with_index{|_,index| index>2} 

如何在迭代Enumerable时形式化逻辑给出2个数组输出。 当我们只调用单partition它的明确 - 方法行为时,但当它跟踪with_index时,这种结构对我来说变得“神奇”。

谢谢

UPD:条件不在partition的块中,它位于单独的'Enumerable'对象方法块中。此方法为with_index第二级互动对我来说很有意思。为什么with_index的条件会影响分区结果? 这是partition文档中不明确的行为。

4 个答案:

答案 0 :(得分:1)

您可能已阅读过partition的Ruby文档:

  

如果没有给出阻止,则返回枚举器。

> arr = [1,2,3,4,5]
=> [1, 2, 3, 4, 5]
> arr.partition
=> #<Enumerator: ...>

你会在Enumerable中的很多方法的描述中看到相同的内容,但是关于返回的枚举器没有太多细节。

枚举器链接的关键在于each中返回的Enumerator方法的行为。例如,Enumerator 返回的partitioneach方法,其行为类似于partition 。这是您能够传递单个块并获得partitionwith_index的组合行为的方式。如果您通过几个步骤执行此操作可能会有所帮助:

> enumerator = arr.partition
=> #<Enumerator: ...>
> enumerator.each { |n| n < 3 } # just to demonstrate `each` performing a partition
=> [[1, 2], [3, 4, 5]]
> enumerator.with_index { |_, index| index > 2 }
=> [[4, 5], [1, 2, 3]]

考虑它的另一种方法是partition没有给出阻止就像将:partition传递给enum_for,例如

> another_enum = arr.enum_for(:partition)
=> #<Enumerator: ...>
> another_enum.with_index { |_, index| index > 2 } # same result as above
=> [[4, 5], [1, 2, 3]]

答案 1 :(得分:0)

当索引是&gt; 2 ruby​​使用其余值创建一个新数组

答案 2 :(得分:0)

<强>分区

  

返回两个数组,第一个包含枚举的元素,块的计算结果为true,第二个包含其余的数组。   如果没有给出块,则返回枚举器。

arr = [1,2,3,4,5]
arr.partition.with_index{|_,index| index>2} 
=> [[4, 5], [1, 2, 3]]

第一个数组将包含[4,5],因为它满足条件index > 2

第二个数组将包含所有其他元素:[1,2,3]

答案 3 :(得分:0)

您正在将Enumerable模块和Enumerator类混合在一起。 Enumerable模块中的所有方法都是实例方法,要求其接收者为枚举器(Enumerator类的实例)。

您可以在自定义类中使用“ include Enumerable”,并实现一个返回枚举器的each方法:

def each
  return enum_for(:each) unless block_given?

  @apples.each { |apple| yield apple }
end

在包含Enumerable的类的实例上执行Enumerable中包含的方法时,Ruby会在该实例与Enumerable方法之间隐式插入该方法。

with_index不是可枚举模块的方法。它是Enumerator类的实例方法。现在记得我说过,当您在自定义类中包含Enumerable模块并实现一个each方法时,该方法可用于返回一个枚举器实例。因此,每个方法都有一个返回枚举数的类可以通过(明确地)在类的实例和with_index之间插入每个方法来使用Enumerator#with_index方法。或者它可以在可枚举的模块方法上调用with_index,因为它会返回一个枚举器实例:

arr = [1,2,3,4,5]
arr.partition.with_index{|_,index| index>2} 

在上面的示例中,partition是Enumerable模块的实例方法,而with_index是Enumerator类的实例方法。分区返回一个枚举器实例,该实例可以使用with_index。

现在要了解该语句的作用,您只需查看可解释分区作用的Enumerable文档:

返回两个数组,第一个包含该块求值为true的enum元素,第二个包含其余的数组。

因此,在您的情况下,它将确定索引是否大于2。如果是,则将其放入一个数组中,否则放入另一个数组中。