The following is a Ruby code snippet from Why’s Poignant Guide to Ruby Chapter 6, where he attempts to demonstrate metaprogramming in Ruby:
# Get a metaclass for this class
def self.metaclass; class << self; self; end; end
I am not that well acquainted with Ruby, but is this what it would look like in expanded form?
def self.metaclass
def self.self
end
end
At least that’s how I understand it. However, it still don’t comprehend what this code does, exactly. What is its purpose?
Further on in the code, Why adds this:
arr.each do |a|
metaclass.instance_eval do
define_method( a ) do |val|
@traits ||= {}
@traits[a] = val
end
end
end
If I understand it correctly, this piece of code adds a new value to @traits with the given name and value. Is that correct?
Thanks for your help, here’s the full source code that caused me trouble, for anyone who wants to see it:
# The guts of life force within Dwemthy's Array
class Creature
# Get a metaclass for this class
def self.metaclass; class << self; self; end; end
# Advanced metaprogramming code for nice, clean traits
def self.traits( *arr )
return @traits if arr.empty?
# 1. Set up accessors for each variable
attr_accessor *arr
# 2. Add a new class method to for each trait.
arr.each do |a|
metaclass.instance_eval do
define_method( a ) do |val|
@traits ||= {}
@traits[a] = val
end
end
end
# 3. For each monster, the `initialize' method
# should use the default number for each trait.
class_eval do
define_method( :initialize ) do
self.class.traits.each do |k,v|
instance_variable_set("@#{k}", v)
end
end
end
end
# Creature attributes are read-only
traits :life, :strength, :charisma, :weapon
end
And in usage:
class Dragon < Creature
life( 1340 ) # tough scales
strength( 451 ) # bristling veins
charisma( 1020 ) # toothy smile
weapon( 939 ) # fire breath
end
In short: what you are seeing defines a method named
metaclasson theCreatureclass itself (not for instances). When you run this method, it finds the metaclass ofCreatureand returns that.Read around the ‘net for what the “metaclass” of an object is.