Coroutines (via fibers) in Ruby 1.9

As a followup to the post below, here is some example code using fibers to implement co-routines. This works in today's snapshot build, but it uses brand-new stuff, so it probably won't work if your build is more than a day old. Similarly, the API may change again, so it might not work if your snapshot is too new, either. svn.ruby-lang.org seems to be down (for me at least) right now, so I got my snapshot here: http://www.mirrorservice.org/sites/ftp.ruby-lang.org/pub/ruby/snapshot.tar.gz The code works for me on Linux, but I haven't tested it elsewhere:

f = g = nil

f = Fiber::Core.new { |x|
  puts "F1: #{x}"        
  x = g.transfer(x+1)    
  puts "F2: #{x}"
  x = g.transfer(x+1)
  puts "F3: #{x}"
}

g = Fiber::Core.new { |x|   
  puts "G1: #{x}"           
  x = f.transfer(x+1)
  puts "G2: #{x}"
  x = f.transfer(x+1)
}

f.transfer(100)

This code prints the following

F1: 100
G1: 101
F2: 102
G2: 103
F3: 104

Notice that the code uses the class Fiber::Core, and its instance method transfer. There is also a Fiber class, with a slightly higher-level API involving the instance method resume and the class method yield. I'm not sure exactly how these are intended to be used, but I was able to produce the same output as above using Fiber (instead of Fiber::Core) as follows:

g = Fiber.new { |x|
  puts "G1: #{x}"
  x = Fiber.yield(x+1)   # Can't use resume here: double resume error
  puts "G2: #{x}"
  x = Fiber.yield(x+1)
}

f = Fiber.new { |x|
  puts "F1: #{x}"
  x = g.resume(x+1)
  puts "F2: #{x}"
  x = g.resume(x+1)
  puts "F3: #{x}"
}

f.resume(100)

Update: Koichi SASADA notes on ruby-core:

Fiber::Core and Fiber::Core#transfer is black magic. So I'm planning to rename this class and method to Fiber::DangerousCore::__unsafe_transfer__I_cant_promise_your_program_run_correctly__!

He also says that the Fiber class is a "semi-coroutine" like Python's generator and that the method names Fiber.resume and Fiber::yield are taken from the language Lua. Time to go read up on Lua, I suppose

Books

Comprehensive coverage of Ruby 1.8 and 1.9

"The New Most Important Ruby Book"
Peter Cooper,
rubyinside.com

Completely updated for Ajax and Web 2.0

"A must-have reference"
Brendan Eich,
creator of JavaScript

The classic Java quick-reference

Advertising

Pages

Hosted By

Powered by Movable Type 4.21-en