Another Take on Smalltalk-Style Controll Flow (SBPP #6)

The latest Smalltalk-to-Ruby translation in my SBPPRB archive is “Dispatched Interpretation”. It’s one of the bigger ones I’ve tackled so far. I’m not going to go over the whole pattern here; for that you’ll just need to buy a copy of Smalltalk Best Practice Patterns 🙂

However, one potentially interesting snippet is this one:

class Object
  def if_false
    self
  end
end

class TrueClass
  def if_true
    yield
  end
end

class FalseClass
  def if_false
    yield
  end

  def if_true
    self
  end
end

This is another take on Smalltalk-style method-based control flow. Specifically, the following Smalltalk idiom:

aPredicate ifTrue: [ ... ] ifFalse: [ ... ]

The key difference here from our last foray into Smalltalk-style flow control is a special implementation of #if_true on FalseClass, which ignores the given block and instead returns itself. This enables a call to #if_false to be chained onto the #if_true call, and the #if_false defined on FalseClass then yields to its block in order to execute the negative case.

On the flip side, if the initial object is true, then TrueClass#if_true method is hit, which yields to the given block. It returns the result value of the block, which, assuming it is not false, will respond to #if_false with the do-nothing method we defined on Object. There is an obvious bug in the case where the block given to if_true does, in fact, return the false constant. I’ll leave fixing that bug as an exercise to the reader.

Bugs aside, the upshot is a chained call idiom which looks not unlike the Smalltalk keyword argument version:

object.if_true{ puts "true!"}.if_false{ puts "false!"}

As with some of the other Smalltalk-in-Ruby articles, I put this forward as a curiosity. If you really want to use method-based flow control pervasively, Ruby might not be the best language for it.

[boilerplate bypath=”sbpp”]

2 comments

  1. I think this: https://gist.github.com/1389177 will do the same thing, but has fewer moving parts?  In your example wouldn’t you also want to add the methods on to NilClass?

Leave a Reply

Your email address will not be published.

Success message!
Warning message!
Error message!