Created
June 6, 2014 13:51
-
-
Save anonymous/efca2c57968d65de20bd to your computer and use it in GitHub Desktop.
Assigning random data for class vs metaclasses
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class Animal | |
def initialize | |
@heads = rand(10) | |
@legs = rand(10) | |
end | |
end | |
# irb(main):001:0> Animal.new | |
# => #<Animal:0x88cf1b0 @heads=3, @legs=4> | |
# irb(main):002:0> Animal.new | |
# => #<Animal:0x8b8b0fc @heads=5, @legs=9> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class Metaid | |
def self.metaclass; class << self; self; end; end | |
def self.traits( *arr ) | |
return @traits if arr.empty? | |
attr_accessor( *arr ) | |
arr.each do |a| | |
metaclass.instance_eval do | |
define_method( a ) do |val| | |
@traits ||= {} | |
@traits[a] = val | |
end | |
end | |
end | |
class_eval do | |
define_method( :initialize ) do | |
self.class.traits.each do |k,v| | |
instance_variable_set("@#{k}", v) | |
end | |
end | |
end | |
end | |
end | |
class Animal < Metaid | |
heads rand(10) | |
legs rand(10) | |
end | |
# irb(main):001:0> Animal.new | |
# => #<Human:0x8138370 @heads=8, @legs=2> | |
# irb(main):002:0> Animal.new | |
# => #<Human:0x83ee790 @heads=8, @legs=2> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
You need to be aware of when a method is called.
Let's look at this line:
This line does this:
Animal.heads(rand(10))
. It's just a regular method call. In a method call, all arguments are evaluated first. So it will first callrand(10)
(and let's say it returns8
) and then it will invoke theAnimal.heads
method with8
as the first argument.The method
Animal.heads
looks like this:Let's look at the case for
Animal.heads(8)
:Notice how the information about
rand(10)
is completely "gone".You can do this same exercise for the class which does
rand(10)
in the initializer to see why it behaves differently.