Rubyには配列やハッシュを操作するメソッドが幾つもありますが、要素を削除するのがdeleteメソッドです。ただし、deleteメソッドはeachメソッドと同時に使用してはいけません。また、deleteメソッドに似た機能のメソッドが他にもあり、それを使うのが適しているケースもあります。
今回は、Rubyで要素を削除するdeleteメソッドについて、その基本や使い方などを解説します。
Rubyのプログラムは配列が重要
今回紹介するRubyのdeleteメソッドは、配列やハッシュなどの要素を削除するメソッドです。Rubyにはdeleteメソッド以外にも、配列やハッシュを操作するための多くのメソッドが用意されています。それだけ、配列やメッシュが、プログラムの中でよく使われるということです。
deleteメソッドを解説する前に、配列やハッシュの要素に対する処理の重要性について解説します。
配列の操作に対する重要性
Rubyに限らず、プログラムを書く際に重視すべきことは、やりたいことに合わせたデータ構造を作成し、それに対する処理を構築する点です。そして、そのデータ構造に使われるのが、配列、または、ハッシュです。
そのため、できるプログラマーになりたいなら、配列やハッシュを操作するスキルを身に付けると良いでしょう。具体的には、作りたいプログラムに合わせて、配列やハッシュによりデータ構造を考えてから、その要素を操作するアルゴリズムを検討すると、効率の良いプログラムが作れます。
Rubyでプログラムを作る場合も、配列やハッシュによるデータ構造を考えてから、それを操作するプログラムを作れるようになりましょう。
Rubyは配列のメソッドが豊富
Rubyには、配列やハッシュを操作するメソッドがたくさん用意されています。それだけ、プログラミングしやすい言語と言えるでしょう。
ただし、それだけ多いということは、似たようなメソッドも多い、ということです。今回紹介するdeleteメソッドと似た機能のメソッドとしてdelete_ifがあり、さらに配列にはdelete_atもあります。
Rubyの数多いメソッドの機能を正しく理解し、それらをうまく活用できるようになりましょう。
deleteメソッドの基本
先ほど説明したように、Rubyのプログラムでは、配列やハッシュに対する操作が重要です。配列やハッシュの要素を操作するメソッドは、正しく理解しなければなりません。
次から、配列やハッシュの要素を削除するdeteteメソッドについて解説します。
配列クラスのdeleteメソッドの文法
配列(Array)クラスの要素を削除するメソッドが、deleteです。そして、deleteメソッドは、指定された値と等しい要素を削除し、その削除した要素を返します。また、指定した値が配列の要素に無かった場合の戻り値はnilです。
Arrayクラスのdeleteメソッドの文法
配列.delete(値)
deleteメソッドを使った簡単な例
arr = [ 1, 2, 3, 4, 5 ] p arr.delete(2) # 配列arrから2が削除され、deleteメソッドが返す2を表示する p arr # 2が削除された配列 [1, 3, 4, 5 ] を表示する
ハッシュクラスのdeleteメソッドの文法
Rubyでは配列(Array)とハッシュ(Hash)は、別のクラスですが、要素を操作するメソッドは同じで、ハッシュでもdeleteメソッドが利用可能です。そして、配列のdeleteでは値を指定して、一致する要素を削除しましたが、ハッシュではキーを指定し、そのキーに該当する要素を削除します。
また、配列のdeleteメソッドと同じく、ハッシュのdeleteメソッドも、削除した要素を返し、該当するキーが無い場合の戻り値はnilです。
Hashクラスのdeleteメソッドの文法
ハッシュ.delete(キー)
deleteメソッドを使った簡単な例
hash = {:a => 1, :b => 2, :c => 3 } p hash.delete(:b) # ハッシュのhashから:b => 2を削除し、deleteメソッドが返す2を表示する p hash # :b => 2が削除されたハッシュ{:a => 1, :c => 3}を表示する
文字列クラスのdeleteメソッドの文法
Rubyでは、文字列を、個々の文字が配列のように並んだ変数だと考えれば、配列のように扱えます。そして、文字列を扱うStringクラスには、配列のdeleteメソッドと同じように使えるdeleteメソッドが用意されています。
Stringクラスのdeleteメソッドは、文字列から特定の文字を削除し、削除した文字を返します。ただし、文字列に適用した場合は、配列やハッシュと違い、元の文字列はそのままです。
Stringクラスのdeleteメソッドの文法
文字列.delete(削除文字)
deleteメソッドを使った簡単な例
str = "012345" p str.delete("2") # 文字列012345から2を削除すた文字列、"01345"を表示する p str #配列やハッシュと違い、元の文字列はそのままなので"013345"を表示する
なお、削除する文字を指定する場合は、正規表現で複数の文字を指定するこができます。
deleteメソッドを使う際の注意点
配列やハッシュをプログラムで利用する場合、eachメソッドによる繰り返し処理をよく利用します。しかし、eachメソッドの繰り返しの中で要素を削除してしまうと、正常な処理ができません。代わりにdelete_ifメソッドを利用してください。
次からeachメソッドとdeleteメソッドを使う場合の注意点とdelete_ifメソッドの使いカについて解説します。
eachメソッドの途中で要素を削除する危険性
eachメソッドは、配列の要素分だけ繰り返し処理が作れる便利なメソッドです。しかし、その要素をdeleteメソッドで削除してしまうと、正常に動作しません。具体的には、次の例を見てください。
sample_arr = [11, 12, 3, 4, 15 ] sample_arr.each { |item| if item < 10 sample_arr.delete(item) end } p sample_arr
この例では、sample_arrという配列の要素を順に評価し、もし、10より小さい数字の場合は、その要素を削除します。では、今の要素が削除されたら、each文で次の要素に移るでしょうか。実は、そうはなりません。今処理中の要素が削除されたことで、次の要素が今処理中の要素となり、次に移るので、1つの要素を飛ばしてしまいます。
そのため、先ほどの例を実行すると、[11, 12, 4, 15]が表示されます。4は、deleteメソッドで削除されるはずですが、1つ前の3を削除した際に、並びが1つずれてしまい、処理されませんでした。
eachの代わりにdelete_ifを使う
先ほど紹介したように、eachメソッドとdeleteメソッドの組み合わせは、誤動作するので使用できません。もし、要素を評価し、その結果に応じて要素を削除したいなら、delete_ifメソッドを使いましょう。
delete_ifの文法
配列.delete_if { |要素を操作するための変数| 削除する条件 }
delete_ifメソッドは、deleteメソッドと同じく、ハッシュでも使えます。
ハッシュ.delete_if { |キーの変数, 要素の変数| 削除する条件 }
先ほどの例を、delete_ifメソッドで書き換えたコードが次の例です。
sample_arr = [11, 12, 3, 4, 15 ] sample_arr.delete_if { |item| item < 10 } p sample_arr
この例では、配列sample_arrに対してdelete_ifメソッドを適用し、要素をitemとし、item < 10に該当する要素を削除します。そして、この場合の出力は、[11, 12, 15]です。
配列の位置で削除するならdelete_at
これまで紹介したdeleteメソッドやdelete_ifメソッドでは、配列の何番目の要素を削除する、というケースでは使えません。この場合は、deletel_atメソッドを使います。delete_atは、配列の添え字の数字を指定することで、その要素を削除します。
なお、delete_atメソッドは、ハッシュに対しては使えません。
delete_atの文法
配列.delete_at( 位置 )
delete_atの使用例
arr = [ 1, 2, 3, 4, 5 ] p arr.delete_at(0) # 配列arrayの最初の要素、array[0]の1を削除し、1を返す p arr # 1が削除されたので、[2, 3, 4, 5 ] を表示する
まとめ
これまで解説したように、Rubyのdeleteメソッドは、配列またはハッシュの中から、指定した要素を削除するメソッドです。ただし、eachメソッドの繰り返しの中で使用すると正しく動作しません。そのような場合は、delete_ifメソッドを利用してください。
また、配列の番号を指定して、その要素を削除するdelete_atメソッドもあります。配列やハッシュの要素を扱うRubyのプログラムでは、今回紹介したdeleteメソッドをうまく活用してください。