深刻解析Java的包(package)。本站提示廣大學習愛好者:(深刻解析Java的包(package))文章只能為提供參考,不一定能成為您想要的結果。以下是深刻解析Java的包(package)正文
instance_eval辦法
這個BasicObject#instance_eval有點相似JS中的bind辦法,分歧的時,bind是將this傳入到對象中,而instance_eval則是將代碼塊(高低文探針Context Probe)傳入到指定的對象中,一個是傳對象,一個是傳履行體。經由過程這類方法便可以在instance_eval中的代碼塊裡拜訪到挪用者對象中的變量。
示例代碼
class MyClass def initialize @v = 1 end end obj = MyClass.new obj.instance_eval do self #=> #<MyClass:0x33333 @v=1> @v #=> 1 end v = 2 obj.instance_eval { @v = v } obj.instance_eval { @v } # => 2
另外,instance_eval辦法還有一個雙胞胎兄弟:instance_exec辦法。比擬前者後者加倍靈巧,許可對代碼塊傳入參數。
示例代碼
class C def initialize @x = 1 end end class D def twisted_method @y = 2 #C.new.instance_eval { “@x: #{@x}, @y>: #{y}” } C.new.instance_exec(@y) { |y| “@x: #{@x}, @y: #{y}” } end end #D.new.twisted_method # => “@x: 1, @y: ” D.new.twisted_method # => “@x: 1, @y: 2”
由於挪用instance_eval後,將挪用者作為了以後的self,所以感化域改換到了class C中,之前的感化域就不失效了。這時候假如還想拜訪到之前@y變量,就須要經由過程參數打包上@y一路隨instance_eval本義,但由於instance_eval不克不及攜帶參數,所以應用其同胞兄弟instance_exec辦法。
instance_eval 與 class_eval 的差別
###instance_eval
起首從名字可以獲得的信息是,instance_eval的挪用者receiver必需是一個實例instance,而在instance_eval block的外部,self即為receiver實例自己。
obj_instance.instance_eval do self # => obj_instance # current class => obj_instance's singleton class end <!--more-->
依據這個界說,假如在一個實例上挪用了instance_eval,便可以在個中界說該實例的單態函數 singleton_method
class A end a = A.new a.instance_eval do self # => a # current class => a's singleton class def method1 puts 'this is a singleton method of instance a' end end a.method1 #=> this is a singleton method of instance a b = A.new b.method1 #=>NoMethodError: undefined method `method1' for #<A:0x10043ff70>
異樣,由於類class自己也是Class類的一個實例,instance_eval也能夠用在類上,這個時刻便可以在個中界說該類的singleton_method,即為該類的類函數。
換句話說,可以用instance_eval來界說類函數class method,這比擬輕易混雜,須要弄清晰。
class A end A.instance_eval do self # => A # current class => A's singleton class def method1 puts 'this is a singleton method of class A' end end A.method1 #=> this is a singleton method of class A class_eval
###class_eval
再來看class_eval,起首從名字可以獲得的信息是,class_eval的挪用者receiver必需是一個類,而在class_eval block的外部,self即為receiver類自己。
class A end A.class_eval do self # => A # current class => A end
依據這個界說,假如在一個類上挪用了class_eval,便可以在個中界說該類的實例函數 instance_method
class A end a = A.new a.method1 #=> NoMethodError: undefined method `method1' for #<A:0x10043ff70> A.class_eval do self # => A # current class => A def method1 puts 'this is a instance method of class A' end end a.method1 #=> this is a instance method of class A
換句話說,可以用class_eval來界說實例函數instance method,這也比擬輕易混雜,須要弄清晰。