superキーワード
Rubyのsuper
class Parent
def speak(word)
word
end
endclass Child < Parent
def speak(word)
super
end
endchild = Child.new
puts child.speak('hello') => hello
- スーパークラス(またはインクルードしたモジュール)のメソッドを呼び出す構文。両方に定義されている場合はモジュールのメソッドが優先される。
- superの呼び元メソッドと同名のインスタンスメソッドを
直上のスーパークラスから探す。二つ以上上のスーパークラスのメソッドを呼ぶことは出来ない。 - インスタンスメソッドの中でのみ使える。クラスメソッドの中でsuperを記述するとエラーになる。
- 引数無しでsuperを呼んだ場合は、super呼び元メソッドに渡された引数と同じ引数がスーパークラスのメソッドに渡される。
- 引数をつけてsuper(var1,va2,...)を呼んだ場合は、その引数をスーパークラスのメソッドに渡す。
Javaのsuper
// スーパークラス側
String speak(String word){
return word;
}// サブクラス側
String meth(String word){
return super.speak(word);
}
RubyとJavaのコンストラクタの動作の違い
このコードを実行しても何も出力されない。
class HogeSuper
def initialize
puts 'hello'
end
endclass Hoge < HogeSuper
def initialize
end
endHoge.new
Javaであれば、Hogeのコンストラクタにsuperが自動で挿入されてhelloが出力されるが、Rubyのinitializeメソッドはsuperを明示的に書かなければスーパークラスのinitializeを呼ぶことはない。
次に、上のコードを以下のように修正する。
実行するとhelloと出力される。
class HogeSuper
def initialize
puts 'hello'
end
endclass Hoge < HogeSuper
endHoge.new
これはJavaの場合と同じ結果だが、内部の動作は違う。
Javaの場合、コンストラクタを省略するとデフォルトコンストラクタが定義され、
その中にsuper()が挿入されることでスーパークラスのコンストラクタが呼ばれる。
Rubyの場合は、initializeが定義されていないクラスをnewすると、単純にスーパークラスから受け継がれたinitializeメソッドが呼ばれる。
結局のところinitializeメソッドは、newメソッドによって呼ばれるというだけで本質は他の一般的なメソッドと変わらない。
ちなみにObjectクラスに空のinitializeメソッドが定義されているので、どんなオブジェクトもinitialize呼び出しに答えられる。