2016-11-01 41 views
0

在Ruby中,爲什麼我不能在模塊的self.included方法中直接設置變量的值在`self.included`內設置變量

例如,下面的代碼輸出NilClass(指示@sound變量沒有被設置):

module Animal 
    def self.included(klass) 
    attr_accessor :sound 
    @sound = "Woof!" # <-- Variable assignment 
    end 

    def speak 
    puts @sound.class 
    end 
end 

class Dog 
    include Animal 
end 

dog = Dog.new 
dog.speak # => NilClass 

但是,如果我模塊的speak方法(代替的內部中設置的@soundself.included),然後該變量設置正確。例如,下面的代碼輸出String

module Animal 
    def self.included(klass) 
    attr_accessor :sound 
    end 

    def speak 
    @sound = "Woof!" # <-- Variable assignment 
    puts @sound.class 
    end 
end 

class Dog 
    include Animal 
end 

dog = Dog.new 
dog.speak # => String 

我本來期望上述輸出String兩個代碼示例。

+0

如果您從另一個角度思考它會更有意義:哪個'狗'的'@聲音'應該包括在內?他們全部?您是否真的想爲'狗'尚未設置'@聲音'的狗'初始化默認值? – Linuxios

回答

2

在第一示例中self.included塊接收機Dog類,而不是它的實例,這意味着你正在定義類實例變量@sound,不實例變量。

您可以通過運行

Dog.instance_variable_get(:@sound) # with first example 

speak方法檢查返回NilClass因爲dog沒有定義@sound實例變量。

在第二個例子中要定義實例變量@sound,因此它可以作爲你的期望。

+0

啊!這現在更有意義了。謝謝!如果有人在乎,基於這個答案,我重新編寫了我的代碼:http://paste.ofcode.org/mkAEyhmPWANfthk2E9rY66 – filmnut