Rubyは、「オブジェクト指向」のプログラミング言語です。
オブジェクトの種類
下記のものを「オブジェクト」として扱います。
- 文字列(Stringクラス)
- 配列(Arrayクラス)
- 数値(Integer、Floatクラス)
- 範囲(Rangeクラス)
- nil(Javaで言えば、nullのことです。)
- 論理値(true/false)
Arrayクラス
配列は、複数の値をまとめて格納できるオブジェクトのことです。インデックス(添え字)を指定することで、値を取り出したり、追加削除したりできます。なお、配列はArrayオブジェクトになります。
他の言語で言うところのコレクションみたいな感じで柔軟にRubyでは処理することができるのです。
構文
1 |
変数 = ['値1', '値2', '値3'] |
数値、文字、配列を一つの配列で混在させることは可能ですが一つのデータ型で統一して使うことが一般的です。
使用例
配列の定義
1 2 3 4 5 6 7 8 9 10 11 |
#配列の定義 animal = ['dog', 'cat', 'monkey'] #1つ目の値 puts animal[0] #2つ目の値 puts animal[1] #0〜10の要素を持つ配列を作成する。 (0..10).to_a |
%記法
%w
シングルクオートでくくったのと同じ動作になります。
1 |
%w[文字1 文字2] |
%W
ダブルクオートでくくったのと同じ動作になります。なので、式展開を埋め込むだったりの記法が使えたりします。
1 |
%W[文字1 文字2] |
%i
シンボルの配列を作ることができます。
1 |
%i[ シンボル名1 シンボル名2 ] |
配列の最後の要素を取り出す。最後から2番目の要素を取り出す。
1 2 3 4 5 6 7 8 |
#配列の定義 numbers = [1,2,3,4,5] #配列の最後の要素の取り出し。 puts numbers[-1] #配列の最後から2番目の要素の取り出し。 puts numbers[-2] |
配列の特定の要素を範囲で抜き出す。
1 2 3 4 5 |
#配列の定義 numbers = [1,2,3,4,5] #配列の2番目から4番目の要素を抜き出す。 puts numbers[1..3] |
配列の値の変更
1 2 3 4 5 |
#配列の定義 animal = ['dog', 'cat', 'monkey'] #2つ目の値を変更する。 animal[1]='elephant' |
配列の末尾に値を追加する。
Javaとかだと、配列は最初に指定した分のサイズしか使うことが出来ませんでしたが、Rubyでは自由に値を追加することができます。
1 2 3 4 5 6 7 8 9 10 |
#配列の定義 animal = ['dog', 'cat', 'monkey'] #末尾に値を追加する。 animal << 'elephant' puts animal[3] #末尾に値を追加する(pushを使う方法) animal.push('elephant') |
配列の最初の要素を削除して返す。
1 |
配列.shift |
配列の特定の要素を削除する。
添字の番号を指定して削除(delete_at)
配列の特定の添え字自体を削除することもできます。
1 2 3 4 5 6 7 |
#配列の定義 animal = ['dog', 'cat', 'monkey'] #2番目の値を削除する。 animal.delete_at(1) puts animal[1] |
特定の要素を全て削除する(delete)
1 2 3 4 5 6 7 |
#配列の定義 animal = ['dog', 'dog', 'monkey'] #特定の要素を削除する。 animal.delete('dog') puts animal |
条件付きで要素を削除する(delete_if)
1 2 3 4 5 6 7 8 9 10 11 |
#配列の定義 numbers = [1,2,3,4,5] #条件に一致した要素のみ削除(2で割り切れる値のみ削除) numbers.delete_if do |number| if number % 2 == 0 true end end puts numbers |
配列の末尾の要素を削除して返す。
1 |
配列.pop |
配列を繰り返し処理させる
配列の要素は繰り返し処理させることができます。他の言語では、for文を使ったりすると思いますが、Rubyでは、基本的にfor文は使わず、「eachメソッド」を使います。
1 2 3 4 5 6 7 |
#配列の定義 animals = ['dog', 'cat', 'monkey'] #繰り返し処理させる animals.each do |animal| puts animal end |
ブロック
eachメソッドの後に指定した「do 〜end」までの部分のことをブロックと呼びます。「{}」(結合度は変わるが)に書き換えることも可能です。ブロックの内部ではRubyのコードを自由に記述することができます。
配列のメソッド
empty?
配列が空かどうか判定します。
include?('文字列')
文字列が配列に存在するかチェックします。
find(エイリアスはdetect)
ブロックの戻り値が真になった最初の要素を返します。
reverse
配列の並び順を反転します。
shuffle
ランダムに値をシャッフルします。
select(find_all)
各要素に対してブロックを評価して、戻り値が真になる要素のみを集める。
1 |
numbers.select {|number| 条件} |
reject
selectとは逆にブロックの戻り値が偽になる要素のみを集めるメソッドです。
uniq
配列内で重複する要素を削除します。
join('区切り文字')
配列内の要素を任意の区切り文字で区切って結合する。
sort
配列内の要素を並び替える。
mapメソッド(エイリアスメソッドとしてはcollect)
新しい配列の形を作り直すことができます。
1 2 3 |
%w[文字1 文字2].map { |str| "({#str})" } => ["({#str})", "({#str})"] |
injectメソッド(エイリアスはreduce)
配列の値をループして合計値及び値を同時に持つためのメソッドです。
1 |
配列.inject { |total,n| total + n } |
範囲(Rangeクラス)
(0..10).to_aとかの「(0..10)」の部分を範囲オブジェクトと呼びます。配列に変換する時とかに使います。なお('a'..'z')等指定して英字の範囲を指定することも可能です。
.が2つ:(0..10).to_a
0〜10までを示します。
.が3つ:(0...10).to_a
0〜9までを示します。(最後の数字を除きます。)
メソッドの呼び出し方
メソッドは下記のように呼び出せます。「()」は省略することも可能です。
- オブジェクト名.メソッド名(引数1,引数2)
- オブジェクト名.メソッド名 引数1,引数2
- オブジェクト名.メソッド名
オブジェクトのクラス名を確認する。
classメソッド
例えば、下記のように文字列に対してclassメソッドを呼び出します。
1 |
puts 'test'.class |
実行結果
文字列は、Stringクラスに属するので下記のような結果になります。
object_idメソッド
オブジェクトのIDを調べることができます。
ガベージコレクション(GC)
Rubyでは、使用されなくなったオブジェクトを回収して、自動的にメモリを解放する仕組みがあるので、プログラマはメモリ管理を意識する必要はないです。
クラス
一種のデータ型で、オブジェクトは必ず何かしらのクラスに属します。なお、クラス構文を使わずにも記述できますが、その場合は「mainという名前のObjectクラスのインスタンス」に属するようになります。(それをトップレベルと言ったりします。)
オブジェクト/インスタンス/レシーバ
クラスから生成します。同じクラスから複数の異なるオブジェクトを生成することも可能です。
なお、「オブジェクト」と「インスタンス」は同じ意味と捉えて問題ありません。
レシーバとは?
なお、オブジェクトからメソッドを呼んだ際に、オブジェクトが格納される変数のことを「レシーバ」と呼んだりします。例えば下記のようなインスタンスの生成処理があったとした場合には変数「user」がレシーバになります。
1 |
user = User.new('太郎',20) |
基本的には、呼び方が異なるだけで「レシーバ」も「オブジェクト」や「インスタンス」と同じ意味になるので、覚えておきましょう。
メソッド/メッセージ
オブジェクトが持つ処理をまとめたもののことです。
状態(ステート)
オブジェクトが保持しているデータのことです。Javaで言うところのフィールドですね。
属性(アトリビュート/プロパティ)
外部から、取得したり、変更したりできるデータのことです。
クラスを作るメリット
ハッシュ(キーと値の組み合わせ)では管理しきれないようなある程度の規模のデータ型を作りたい場合に使います。
ハッシュの欠点
- 新しくキーを追加したり削除したりできるので脆くて壊れやすいプログラムになりがち。
- ハッシュだとキーの指定を間違えてもエラーにならずnilが返ってくるのでミスに気付きにくい。
クラスの作り方
構文
1 2 |
class クラス名 end |
例
1 2 3 |
#動物クラスの定義 class Animals end |
なお、クラス名の先頭文字は必ず大文字で始めるようにしましょう。エラーになってしまいます。
クラスを初期化するには?
クラスを初期化する場合は、initializeメソッドを実装します。Javaで言えば、「コンストラクタ」といったところでしょうか。
特徴としては、initializeメソッドは、newした際にだけ呼び出される外部から呼び出すことができないメソッドです。
例
1 2 3 4 5 6 |
#動物クラスの定義 class Animals def initialize puts '初期化処理' end end |
initializeメソッドに引数を渡して、インスタンス変数を初期化したりすることもできます。
クラスの使い方
newして使います。
1 2 3 4 5 6 7 8 9 |
#動物クラスの定義 class Animals def initialize puts '初期化処理' end end #クラスをnewする。 Animals.new |
メソッドを定義及び実行するには?
インスタンスメソッド
1 2 3 4 5 6 7 8 9 10 11 |
#動物クラスの定義 class Animals def helloWorld puts 'Hello World!' end end #クラスをnewする。 animal = Animals.new #メソッドを実行する。 animal.helloWorld |
なお、上記のメソッドはnewしたインスタンスから呼び出せる「インスタンスメソッド」と呼びます。
とあるインスタンスの情報を取り出したい場合はこちらのメソッドを使います。
また、同じクラス内の別メソッドから他のインスタンスメソッドを呼び出す場合は下記のように記載します。(selfは省略できます。)
1 |
self.別インスタンスメソッド |
クラスメソッド
クラスのメソッド名に「self」をつけることでそのメソッドは「クラスメソッド」になりnewしなくても直接呼び出せるようになります。呼び出す際はinitializeメソッドは実行されません。なお、newして作成したインスタンスからは呼び出すことができないので注意です。
一つのクラスメソッド を定義する方法
1 2 3 4 5 |
class クラス名 def self.クラスメソッド名 ##処理内容 end end |
クラス全体(全てのインスタンス)の中から必要な情報を取り出したい場合はこちらを使います。
複数のクラスメソッド をまとめて定義する方法
下記のように記述することで複数のクラスメソッド をまとめて定義することが可能です。
1 2 3 4 5 6 7 8 9 |
class クラス名 class << self def クラスメソッド名1 end def クラスメソッド名2 end end end |
インスタンス変数を使うには?
インスタンス変数(定義したオブジェクト固有の変数)を使うには、クラス内で「@」を先頭につけた変数を定義します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
#動物クラスの定義 class Animals def initialize(name) @name = name end def helloAnimal puts "Hello #{@name}!" end end #クラスをnewする。 dog = Animals.new('dog') #インスタンス変数に入れた値を表示する。 puts dog.helloAnimal |
外部からインスタンス変数に直接アクセスするには?
アクセサメソッドを定義します。Javaで言うところのゲッター/セッターメソッドのことですね。
Javaのように、get、setとそれぞれメソッドを用意する必要がなく、変数の前に「attr_accessorメソッド」というメソッドを定義をすることで読み書き可能な変数になります。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
#動物クラスの定義 class Animals #読書きができるインスタンス変数 attr_accessor :name def initialize(name) @name = name end end #クラスをnewする。 dog = Animals.new('dog') #インスタンス変数の値を変更 dog.name = 'sibainu' #インスタンス変数の値を表示 puts dog.name |
なお、「読み取り専用」や「書き込み専用」のメソッドも用意されていますが、通常多く利用されるのは、「読み取り専用」のメソッドでしょうね。
メソッド名 | 説明 |
---|---|
attr_accessor | 読み書き可能 |
attr_reader | 読み込みのみ可能 |
attr_writer | 書き込みのみ可能 |
クラス変数について
クラス自体が持つインスタンスに縛られない共通の変数です。「@@クラス変数名」と指定します。
クラス変数にはインスタンスメソッドからもinitializeメソッドからもアクセスは可能です。ちなみにクラス変数は実務ではあまり使用されることはありません。
クラス定数について
下記の記事で紹介していますのでご参照ください。
「継承」について
親クラスを知るには?
下記メソッドを使います。
1 |
クラス名.superclass |
オーバーライド
親クラスと全く同じメソッド名のメソッドを指定すれば親クラスのメソッドを子クラスで上書きできます。Rubyのオーバーライドは「引数の数」とか「引数の型」とかは全く関係なく「メソッド名が単純に一致していた場合」にオーバーライドされるので注意です。
オーバーライドしたメソッドで親クラスのメソッドを呼び出すには?
下記の記述をすればオーバーライドした子クラスのメソッドから親クラスの同名のメソッドを呼び出せます。
1 |
super |
この記事へのコメントはありません。