TOPシステム開発> 第2回:Rubyを動かそう!(3/3)

いまさら聞けないRuby入門

いまさら聞けないRuby入門

第2回:Rubyを動かそう!

著者:伊藤忠テクノソリューションズ  大場 光一郎

公開日:2007/12/3(月)

ブロック

先ほどRubyにはデータとメソッドがあると説明しました。実はRubyにはメソッドのような実行できる処理をもデータと同じように他のメソッドに渡すことができる「ブロック」という仕組みがあります。「ブロック」はRubyの柔軟性を生み出している要素の1つです。

繰り返し処理

ブロックの典型的な活用例がRubyの繰り返し処理です。Rubyでは「イテレータ」と呼びます。では、さっそくirbで試してみましょう(リスト8)。

「do」から「end」までがブロックとなります。これを配列arrayのeachメソッドへ渡しています。eachでは配列の要素1つ1つに対して渡されたブロックを実行しています。この例ではputsを実行して要素を表示しています。

ブロックを活用することによって外側から自由に実行させたい処理の断片を渡すことができるのです。他にもファイルのオープン、クローズなどブロックを活用することが多くあります。

宣言的な記法

Dogクラスには名前を返すメソッド「name」を定義しました。このようにインスタンス変数を参照したり代入したりするメソッドを「アクセサメソッド」と呼び、Rubyではインスタンス変数の都度定義しなくても簡単なメソッドの呼び出しで定義することができます。

アクセサメソッドには次の3種類があり、「attr_accessor」は読み書き可能、「attr_reader」は読み出し専用、「attr_writer」は書き込み専用となっています。

実際にCatクラスでアクセサメソッドを作ってみましょう。nameを読み出し専用としてageを読み書き可能としてみます(リスト9)。

リスト8:ブロックの定義
 irb(main):050:0> array = [1, 2, 3, 4, 5]
  => [1, 2, 3, 4, 5]
  irb(main):051:0> array.each do |e| # <- ブロック開始
  irb(main):052:1* puts e          #  |
  irb(main):053:2> end               # <- ブロック終端
  1
  2
  3
  4
  5
  => [1, 2, 3, 4, 5]

リスト9:アクセサメソッドの定義
  irb(main):060:0> class Cat
  irb(main):061:1>   attr_reader :name
  irb(main):062:1>   attr_accessor :age
  irb(main):063:1>   def initialize(name, age)
  irb(main):064:2>     @name = name
  irb(main):065:2>     @age = age
  irb(main):066:2>   end
  irb(main):067:1> end
  => nil

リスト10:アクセサメソッドの実行
  irb(main):070:0> tama = Cat.new("tama", 10)
  irb(main):071:0> tama.name
  => "tama"
  irb(main):072:0> tama.age
  => 10
  irb(main):073:0> tama.age = 11
  => 11

リスト11:すべてがオブジェクト
  irb(main):080:0> 1.to_s # 数値を文字列に変換します
  => "1"
  irb(main):081:0> 1.class # クラスを表示
  => Fixnum
  irb(main):082:0> "Hello".class
  => String
  irb(main):083:0> tama.class
  => Cat
  irb(main):084:0> 3.times do
  irb(main):085:1* puts "Hello"
  irb(main):086:1> end
  Hello
  Hello
  Hello
  => 3

アクセサメソッドを使ってみます。Catクラスをインスタンス化してtama変数に代入します(リスト10)。

インスタンス変数へ簡単にアクセスできるようになりました。クラスに宣言するように書くだけでメソッドが追加されます。他にも便利なメソッドが用意されています。リファレンスマニュアルのModuleの項を参照してみてください。

Rubyリファレンスマニュアル(Moduleの項)
http://www.ruby-lang.org/ja/man/?cmd=view;name=Module

実習3

読み出し専用属性に書き込んだり、書き込み専用属性を読み込んだりエラーが出るか確かめてみてください。

すべてがオブジェクト

Rubyでは今まで作成したDogやCatのような手作りのクラスだけでなく、システムが用意しているシステムクラスや、単なる数値、文字列に至るまですべてがオブジェクトとして扱えます。数値や文字列もメソッドを持っているのです。それではirbで試してみましょう(リスト11)。

実行環境がオブジェクト

今まで画面に文字列を表示するための命令として「puts」を使ってきました。レシーバ無しで呼び出しているputsは、どのクラスのメソッドなのでしょうか。

実はObjectクラスというRubyのすべてのクラスのベースになるクラスのメソッドです。レシーバ無しで呼んだメソッドは、自分のクラスに該当するメソッドが無ければ、最終的にベースのObjectクラスに定義されたメソッドを呼び出します。そのためObjectクラスに定義されたメソッドはどこからでも呼び出すことができるのです。

オープンクラス

irbを使って少しづつDogクラスのメソッドを増やしていったり、定義を拡張していきました。Rubyではこのように完全なクラスを一度に書かなくても、後から足したり書き換えたりして定義できます。これはRubyの動的な特徴の1つですね。

同じようにRubyが標準で提供する各種クラスライブラリも書き換えたり拡張したりすることができます。ユーザ自身が作ったユーザクラスとシステムが提供するシステムクラスとの区別が無いことを「オープンクラス」と呼びます。

オープンクラスのRubyではシステムクラスやサードパーティから提供されたライブラリを自分の好きな形にカスタマイズすることも可能です。しかし多くのシステムで使われているシステムクラスを安易に書き換えると、Ruby全体に影響がおよぶため十分なテストが必要となりますので注意してください。

まとめ

Rubyとオブジェクト指向プログラミングへの入り口をirbで確かめながら解説してきました。オブジェクト指向は奥が深いですが、オブジェクト指向の理解が進むことでRubyの背景にある設計の意味がわかってきます。Rubyを活用するためにぜひオブジェクト指向プログラミングに親しんでみてください。


前のページ  1  2  3


伊藤忠テクノソリューションズ株式会社 大場 光一郎
著者プロフィール
伊藤忠テクノソリューションズ株式会社  大場 光一郎
社内のRuby推進に従事。個人的にBookScopeの開発に協力する傍ら、オープンソースへの活動としてMeadowプロジェクトに参加したり、JRubyの開発に協力したりしている。最近、Java Expert #02へJRubyの記事を書いた。

Meadow
http://www.meadowy.org/meadow/
BookScope
http://bookscope.net/
暮らしの業
http://ko.meadowy.net/~koichiro/diary/


INDEX
第2回:Rubyを動かそう!
  プログラムを動かそう
  name(名前)やage(年齢)のデータを加える
ブロック