In Scala you can define a stream from its first element, and a function to get the next one from the previous one;
Stream.iterate(1)(x => 2 * x + 1)
Does something exist like this in Ruby?
Of course we can hand roll it-
module Kernel
def stream
Enumerator.new do |y|
that = self
while true
y << that
that = yield that
end
end
end
end
But is it idiomatic? Is there something like this already?
What you are asking about is called an unfold (which is called Stream.iterate
in scala), or more generically, an anamorphism. It is the exact category-theoretical dual of a fold (which is called Enumerable#inject
in ruby) aka a catamorphism.
Is there something like this already ?
Unfortunately, there is no method in the core or standard library which performs this function.
But is it idiomatic ?
I would probably make it a singleton method of Enumerator
and use Kernel#loop
instead of while true
, but that's about it. Otherwise, yes, your code is pretty idiomatic.
And while we're at it, let's call it unfold
:
def Enumerator.unfold(start)
new do |y|
loop do
y << start
start = yield start
end
end
end