改めて言うまでもないことではありますが、Rubyはクラスベースのオブジェクト指向言語なので、クラスを宣言する機能があります。ただし、他の言語と違う点もあります。
他言語でよくあるクラス宣言
C++やJavaはコンパイラ型のオブジェクト指向言語ですが、これらの言語でのクラス宣言は、コンパイル時にコンパイラが処理して構造を生成してしまうものです。そのため、クラス宣言の中には、メンバ変数やメソッドの宣言・定義、それらの可視性の設定といった、限られたことしかできません。
class Invalid{
int m_int;
//宣言以外の実行はできない
std::cout << "Foo!" <<endl;
}
PHPはスクリプト言語ではあるのですが、クラス宣言はC++などと同様、宣言・初期値代入程度しかできません。
Rubyのclass
に入る
一方、Rubyのclass
では、他の言語のようにメソッドなどの宣言もできるのですが、コンテキストこそ変われど、単なるコード実行も可能です。
class Hello
puts 'Hello, World!'
end
このコードを実行すると、Hello
クラスをインスタンス化するまでもなく、Hello, World!
が出力されます。
宣言的構文
もちろん、クラス宣言の中で直接出力を行うことはあまり有用ではないとは思います。ただし、この「クラス宣言の中で実行を行えること」は、多くのRubyプログラムで利用されています。
class Hoge < ActiveRecord::Base
attr_accessor :piyo
validates :fuga, presence: true
#後略
end
Ruby標準ライブラリにあるattr_accessor
も、実はModuleクラスの1メソッドです。ぱっと見た感じでは特殊な宣言構文のようにも見えますが、中身はただのメソッド呼び出しで、実行されたメソッドが必要なメソッドを動的に生成しています(CRubyではC言語で実装してありますが、Rubyでも簡単に実装できます)。
上の実装例でもわかるように、こんな「宣言のようなメソッド」を自分で作ることももちろん可能で、その例としてActiveRecordのバリデーション構文があります。validates
はActiveModel::Validations::ClassMethodsのメソッドで、実行されることでバリデーションを登録しています。