Foo = Class.new
Foo.class_eval do
def class_bar
"class_bar"
end
end
Foo.instance_eval do
def instance_bar
"instance_bar"
end
end
Foo.class_bar #=> undefined method ‘class_bar’ for Foo:Class
Foo.new.class_bar #=> "class_bar"
Foo.instance_bar #=> "instance_bar"
Foo.new.instance_bar #=> undefined method ‘instance_bar’ for #<Foo:0x7dce8>
Просто основанный на имени методов Я бы ожидал, что class_eval позволит вам добавить метод класса в Foo и instance_eval, чтобы вы могли добавить метод экземпляра в Foo. Но они, похоже, делают обратное.
В приведенном выше примере, если вы вызываете class_bar в классе Foo, вы получаете ошибку метода undefined, и если вы вызываете экземплярную строку экземпляра, возвращаемого Foo.new, вы также получаете ошибку метода undefined. Обе ошибки, похоже, противоречат интуитивному пониманию того, что должны делать class_eval и instance_eval.
В чем разница между этими методами?
Документация для class_eval:
mod.class_eval (string [, filename [, lineno]]) = > obj
Вычисляет строку или блок в контекст моды. Это можно использовать для добавьте методы в класс.
Документация для instance_eval:
obj.instance_eval {| | block} = > obj
Вычисляет строку, содержащую Ruby исходный код или заданный блок, в контексте приемника (OBJ). Чтобы установить контекст, переменная self устанавливается равной obj while код выполняет, выдавая код доступ к переменным экземпляра objs.