Tear-off methods in Ruby

Let’s start with the Robot class.

class Robot
  def initialize(x = 0, y = 0)
    @x, @y, = x, y
  end

  def move_right
    @x += 1
  end

  def move_left
    @x -= 1
  end

  def move_up
    @y += 1
  end

  def move_down
    @y -= 1
  end
end

To “tear off” a method in Ruby, we use the method named method. When we give it a symbol, it gives us back a Method object corresponding to that symbol.

require "./robot.rb"

r = Robot.new
# => #<Robot:0x0000000217eb78 @x=0, @y=0>

move = r.method(:move_up)

move
# => #<Method: Robot#move_up>

This Method object isn’t just a reference to a procedure. It also knows what object it came from. Or in other words, the object which should “receive” the message when it is sent.

move.receiver
# => #<Robot:0x0000000217eb78 @x=0, @y=0>

The move object is call-able and we can call it multiple times.

require "./robot.rb"

r = Robot.new

move = r.method(:move_up)

move.call()
move.call()
move.call()

r # => #<Robot:0x0000000211f948 @x=0, @y=3>

If we want, we can use Ruby’s shorthand for call-able objects:

move = r.method(:move_right)

move.()
move.()
move.()

r # => #<Robot:0x0000000211f948 @x=3, @y=3>
Alexander M over 5 years ago
This website uses short-lived cookies to improve usability.
Accept or learn more