Is there a good way to emulate yield
in Ruby? I'm interested in writing similar 'infinite fib sequence' in Ruby.
Here is the code:
using System;
using System.Collections.Generic;
using System.Linq;
namespace cs2 {
clas开发者_开发知识库s Program {
static void Main(string[] args) {
var i=Fibs().TakeWhile(x=>x < 1000).Where(x=>x % 2==0).Sum();
}
static IEnumerable<long> Fibs() {
long a = 0, b = 1;
while (true) {
yield return b;
b += a;
a = b - a;
}
}
}
}
If it is possible, please give an example.
The common idiom in ruby to implement such sequences, is to define a method that executes a block for each element in the sequence if one is given or return an enumerator if it is not. That would look like this:
def fibs
return enum_for(:fibs) unless block_given?
a = 0
b = 1
while true
yield b
b += a
a = b - a
end
end
fibs
#=> #<Enumerable::Enumerator:0x7f030eb37988>
fibs.first(20)
#=> [1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, 233, 377, 610, 987, 1597, 2584, 4181, 6765]
fibs.take_while {|x| x < 1000}.select {|x| x%2 == 0}
#=> [2, 8, 34, 144, 610]
fibs.take_while {|x| x < 1000}.select {|x| x%2 == 0}.inject(:+)
=> 798
Fibonacci numbers with Ruby 1.9 Fibers:
fib = Fiber.new do
x, y = 0, 1
loop do
Fiber.yield y
x,y = y,x+y
end
end
20.times { puts fib.resume }
精彩评论