Module#memoize

A very handy method for method return value memoization:

class Module
  if instance_methods.include?(:memoize)
    raise Exception, "Module#memoize already defined" 
  end

  def memoize(method_name)
    method = instance_method(method_name)

    unless method.arity == 0
      raise "Method `#{method_name}` must not take any arguments but has arity #{method.arity}" 
    end

    ivar_name = "@__memoize__#{method_name}" 

    define_method(method_name) do
      if instance_variable_defined?(ivar_name)
        instance_variable_get(ivar_name)
      else
        value = method.bind(self).call
        instance_variable_set(ivar_name, value)
        value
      end
    end
  end
end

Usage

class SuperComputer
  def answer_to_the_ultimate_question_of_life_the_universe_and_everything
    # ???
  end
  memoize :answer_to_the_ultimate_question_of_life_the_universe_and_everything
end