Hi --

On Sun, 14 May 2006, Pat Maddox wrote:

> I genuinely have no clue what the difference is between class_eval and
> instance_eval.  Check out this quick irb session:
>
> irb(main):111:0> class Foo; end
> => nil
> irb(main):112:0> Foo.instance_eval { define_method(:foo) { "foo" } }
> => #<Proc:0x00318b00@(irb):112>
> irb(main):113:0> Foo.foo
> NoMethodError: undefined method `foo' for Foo:Class
>       from (irb):113
>       from :0
> irb(main):114:0> Foo.new.foo
> => "foo"
> irb(main):115:0> class Bar; end
> => nil
> irb(main):116:0> Bar.class_eval { define_method(:bar) { "bar" } }
> => #<Proc:0x003078a0@(irb):116>
> irb(main):117:0> Bar.bar
> NoMethodError: undefined method `bar' for Bar:Class
>       from (irb):117
>       from :0
> irb(main):118:0> Bar.new.bar
> => "bar"
>
> I would think that since I used class_eval in one and instance_eval in
> the other, SOMETHING should be different..

Fear not; it is :-)  Look at what happens when you use def:

>> class C; end
=> nil
>> C.instance_eval { def x; 1; end }  # singleton method on C
=> nil
>> C.x
=> 1
>> C.new.x
NoMethodError: undefined method `x' for #<C:0x35b16c>
         from (irb):4
         from :0
>> C.class_eval { def y; 1; end } # instance method of C
=> nil
>> C.y
NoMethodError: undefined method `y' for C:Class
         from (irb):6
         from :0
>> C.new.y
=> 1

C.instance_eval handles the business of C itself, as an object.  You'd
get similar results with any_object.instance_eval { def x; 1; end }

C.class_eval takes you into a class definition block for C, where def
is an instance method of C.  So it's much more class (and module)
specific in its engineering.


David

-- 
David A. Black (dblack / wobblini.net)
* Ruby Power and Light, LLC (http://www.rubypowerandlight.com)
   > Ruby and Rails consultancy and training
* Author of "Ruby for Rails" from Manning Publications!
   > http://www.manning.com/black