There's an echo in my head

日々のメモ。

クラス変数とインスタンス変数

class Klass
  @iv  = 1
  @@cv = 2

  def self.iv; @iv  end
  def self.cv; @@cv end

  def iv; @iv  end
  def cv; @@cv end
end

class SubKlass < Klass
end

# クラスのインスタンス変数を参照してみる

Klass.iv    #=> 1
SubKlass.iv #=> nil

Klass.new.iv    #=> nil
SubKlass.new.iv #=> nil

# クラス変数を参照してみる

Klass.cv    #=> 2
SubKlass.cv #=> 2

Klass.new.cv    #=> 2
SubKlass.new.cv #=> 2

クラスのコンテキストで宣言されたインスタンス変数@ivClassクラスのインスタンスKlassに保持されているので、それを継承しているSubKlassには共有されないし、またKlassインスタンスのコンテキストからputs @ivという感じで参照することはできない。なのでインスタンスなど外部から参照する場合には、Klass.instance_variable_get(:@iv)するか、setter/getterメソッドを定義する。

一方クラス変数@@cvは、そうじゃない。どういう仕組みになっているかはわからないけど、SubKlassにも共有されるし、インスタンスのコンテキストからもputs @@cvという感じで参照することができる。

このブログに出てくるコードスニペッツは、引用あるいは断りがない限りMITライセンスです。