Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Continuations in Ruby

Antono Vasiljev
June 17, 2012
130

Continuations in Ruby

Antono Vasiljev

June 17, 2012
Tweet

Transcript

  1. 1: i = 0 2: callcc do |cont| 3: i

    = 1 4: cont.call 5: i = 2 # skipped 6: end 7: 8: # i => 1
  2. 1: i = 0 2: i = callcc do |cont|

    3: i = 1 4: cont.call(2) 5: i = 3 # skipped 6: end 7: 8: # i => 2 # See lines: 2, 4
  3. 1| i = 0 2| 3| label :sum 4| 5|

    puts i += 1 6| 7| goto :sum, cond: (i < 10)
  4. 1| LABELS = {} 2| 3| def label(name) 4| callcc

    { |cont| LABELS[name] = cont } 5| end 6| 7| def goto(label, args: {}) 8| LABELS[label].call if args[:cond] 9| end
  5. continuations jumps far def foo bar end def bar baz

    end def baz $cont[0] end callcc { |c| $cont = c; foo }
  6. 1| begin 2| hello 3| rescue Exception => e 4|

    e.restart 5| ensure 6| e.cleanup 7| end
  7. 1| def hello 3| i = 0 4| restartable do

    5| puts i += 1 6| raise Exception unless i == 5 7| end 8| end
  8. 1| def restartable 2| cont = callcc { |c| c

    } 3| begin 4| yield 5| rescue Exception => e 6| e.continuation = cont 7| raise e 8| end 9| end
  9. require 'continuation' class Exception class << self attr_accessor :conts end

    def continuation=(cont) self.class.conts ||= {} self.class.conts[self.class] ||= cont end