bra*_*rad 5 ruby instance-eval attr-accessor class-eval
我理解instance_eval和之间的基本区别class_eval.我玩的时候发现的东西是奇怪的attr_accessor.这是一个例子:
A = Class.new
A.class_eval{ attr_accessor :x }
a = A.new
a.x = "x"
a.x
=> "x" # ... expected
A.instance_eval{ attr_accessor :y }
A.y = "y"
=> NoMethodError: undefined method `y=' for A:Class
a.y = "y"
=> "y" # WHATTT?
Run Code Online (Sandbox Code Playgroud)
怎么样:
首先,你的理解(或直觉)是正确的,里面定义的方法#instance_eval,并#class_eval是不一样的
A = Class.new
A.instance_eval { def defined_in_instance_eval; :instance_eval; end }
A.class_eval { def defined_in_class_eval; :class_eval; end }
A.new.defined_in_class_eval # => :class_eval
A.defined_in_instance_eval # => :instance_eval
Run Code Online (Sandbox Code Playgroud)
一个侧面说明:虽然self是相同的两个instance_eval和class_eval的默认definee不同的是,看到http://yugui.jp/articles/846
究竟是什么诀窍Module#attr_accessor本身,看看它的定义:http:
//rxr.whitequark.org/mri/source/vm_method.c#620
它不使用def,它不读取上下文self或默认的definee.它只是"手动"将方法插入到模块中.这就是结果违反直觉的原因.