通常のインスタンス変数
class Person
def initialize(name)
@name = name # 通常のインスタンス変数
end
end
person1 = Person.new("Alice")
person2 = Person.new("Bob")
# person1 と person2 は別々の @name を持つ
各インスタンスごとに独立した値を持つ
インスタンスメソッド内でアクセスできる
クラスインスタンス変数
class Person
@count = 0
def self.count
@count
end
end
puts Person.count # => 0
p1 = Person.new # 新しいインスタンスを作成
puts Person.count # => 0(変化なし)
クラス自体に紐づく変数
クラスメソッド内でのみアクセスできる
クラス変数との違い
class Person
@@total = 0 # クラス変数
def self.total
@@total
end
def initialize
@@total += 1
end
end
puts Person.total # => 0 (初期値)
person1 = Person.new # インスタンス作成
puts Person.total # => 1 (1つ目のインスタンス作成で +1)
クラス変数(@@)は継承されたすべてのクラスで共有
クラスインスタンス変数(@)は該当クラスのみに属す
使用例
# クラスインスタンス変数
class Parent
@value = "parent"
def self.value
@value
end
end
class Child < Parent
@value = "child"
def self.value
@value
end
end
puts Parent.value # => "parent"
puts Child.value # => "child"
# クラスインスタンス変数は継承されず、各クラスで独立
# 対してクラス変数の場合:
class Parent
@@value = "parent"
def self.value
@@value
end
end
class Child < Parent
@@value = "child"
end
puts Parent.value # => "child"
puts Child.value # => "child"
# クラス変数は継承階層で共有されてしまう
クラスインスタンス変数へのアクセス方法
class Person
def self.count
@count
end
def self.count=(value)
@count = value
end
end
特異メソッドで上記を書き換えた場合
class Person
# class << self による特異メソッド定義
class << self
def count
@count
end
def count=(value)
@count = value
end
end
end
また、以下のようにattr_accessorもクラスインスタンス変数に対しても使える
クラス変数に関してはattr_accessorは使用できない
class Person
class << self
attr_accessor :count # count と count= の両方を一度に定義
end
end