Ruby, difference from instance_eval and class_eval

posted by Arkham on July 5th, 2011

String.instance_eval { def foo; p "bar"; end }
String.foo = "bar"
String.class_eval { def foo; p "bar"; end }
"sausage".foo = "bar"

So, using instance_eval adds a class method.
On the other hand, using class_eval adds a instance method.

Why?

class_eval is a method of the Module class, meaning that the receiver will be a module or a class. The block you pass to class_eval is evaluated in the context of that class. Defining a method with the standard def keyword within a class defines an instance method, and that’s exactly what happens here.

instance_eval, on the other hand, is a method of the Object class, meaning that the receiver will be an object. The block you pass to instance_eval is evaluated in the context of that object. That means that String.instance_eval is evaluated in the context of the String object. Remember that a class name is simply a constant which points to an instance of the class Class. Because of this fact, defining a method in the context of Class instance referenced by String creates a class method for the String class.

Tags: ,