Skip to content
Reconsidered adds a vital and sorely missed language feature to Ruby: the well known and widely loved GO TO operation.
Ruby
Find file
Fetching latest commit…
Cannot retrieve the latest commit at this time.
Failed to load latest commit information.
examples
lib
test
.autotest
History.txt
LICENSE.txt
Manifest.txt
README.rdoc
README.txt
Rakefile

README.rdoc

reconsidered

github.com/jimwise/reconsidered

Author

Jim Wise (jwise@draga.com)

Copyright

Copyright © 2012 Jim Wise

License

2-clause BSD-Style (see LICENSE.txt)

DESCRIPTION:

Reconsidered adds a vital and sorely missed language feature to Ruby: the well known and widely loved GO TO operation.

OVERVIEW:

As discussed in Donald Knuth's seminal paper {Structured Programming with go to Statements} (see REFERENCES, below), GOTO can be an important part of your structured programming toolkit – but it has not been available in Ruby until now.

However, this implementation is itself severely limited – it only allows execution to jump to a point in the program which has already been passed during execution of the program; it is thus less general purpose a tool than the true GOTO of languages such as Fortran.

REQUIREMENTS:

This code will not work in JRuby or MacRuby (no callcc). It is tested (and should work fine) in Ruby 1.8.7 and 1.9.3.

INSTALL:

To install:

$ gem install reconsidered

SYNOPSIS:

General usage

The syntax here mirrors that of the optional __goto__ extension included (disabled by default) as a joke (see REFERENCES, below) in the Ruby 1.9 sources

You may label any point in your program with the Kernel#__label__ statement, as in:

__label__ 10
puts "Hello, world!"

or

__label__ :guess
print "Can you guess it? "

This creates a global label, which you may return to at any point in your program using the Kernel#__goto__ statement, as in:

__goto__ 10

or

guess = gets.to_i
if num != guess
  puts "Wrong!"
  __goto__ :guess
else
  puts "Right!"
end

The __goto__ statement will immediately resume execution from the last point at which __label__ was called with the same value.

Note that this implies that you may only use __goto__ to return to a __label__ statement which has already been executed, unlike the GOTO statement in, e.g. C, which can be used to jump forward (but only within a given function):

  if (num == guess)
    goto right;
  else
    goto guess;

right:
  puts("Right!")

Working around this limitation is left as an exercise for the reader.

If you try to __goto__ a label which you have not defined (or not yet defined), you're gonna have a hard time (and raise a Reconsidered::NoSuchLabel exception).

Private Labels

In addition to the default global scope used with __label__ and __goto__, you can allocate a private scope of labels using the Reconsidered::Labels class. This class provides methods Labels#label and Lables#goto which can be used as follows:

l = Reconsidered::Labels.new
acc = 0
l.label 30
acc = acc + 1
if acc < 10
  l.goto 30
end

this not only provides a private set of objects (not overlapping with other use of __label__ and __goto__), but has the added advantage that all memory used to store labels within such an object is freed when the object is garbage collected.

DEVELOPERS:

After checking out the source, run:

$ rake newb

This task will install any missing dependencies, run the tests/specs, and generate the RDoc.

REFERENCES:

For competing views on GOTO as a language feature, see

For information on the implementation strategy used here (and the general equivalence of the more powerful call-with-current-continuation operation to go to), see

For information on Ruby's implementation of call-with-current-continuation see

For information on the (different, and less limited) implementation provided in ruby 1.9 as a language feature, but disabled by default, see

LICENSE:

(The MIT License)

Copyright © 2012 FIX

Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the 'Software'), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

Something went wrong with that request. Please try again.