Отлично подходит для больших или бесконечных объектов-генераторов.
Например, следующее даст вам счетчик для всей последовательности Фибоначчи, от 0 до бесконечности.
def fib_sequence
return to_enum(:fib_sequence) unless block_given?
yield 0
yield 1
x,y, = 0, 1
loop { x,y = y,x+y; yield(y) }
end
to_enum
позволяет эффективно писать это с обычным yields
без необходимости связываться с Fiber
s.
Затем вы можете нарезать его по своему усмотрению, и это будет очень эффективно использовать память, поскольку в памяти не будет храниться никаких массивов:
module Slice
def slice(range)
return to_enum(:slice, range) unless block_given?
start, finish = range.first, range.max + 1
copy = self.dup
start.times { copy.next }
(finish-start).times { yield copy.next }
end
end
class Enumerator
include Slice
end
fib_sequence.slice(0..10).to_a
#=> [0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55]
fib_sequence.slice(10..20).to_a
#=> [55, 89, 144, 233, 377, 610, 987, 1597, 2584, 4181, 6765]