3
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

破壊的メソッドとはオブジェクトの内容を変更するメソッドである,のか?

Posted at

Ruby プログラミングを学ぶうえで非常に重要なのが非破壊的メソッドと破壊的メソッドの区別ですよね。
「破壊」だなんて物騒! まるで壊してダメにしてしまうかのような用語ですが,そうではなく,レシーバーであるオブジェクトに変化を与えうるメソッドを「破壊的メソッド」と呼んでいるだけですね。

さて,Ruby の初心者向け記事で

破壊的メソッドとはオブジェクトの内容を変えるメソッドである。

というような説明を非常によく目にします。
どこかのスクールでそう教えてるんでしょうかね?

この記事のテーマは,この言明が果たして正しいのかどうか,ということです。

結論を先に書くと,これは「おおむね正しいが,適切な表現ではない」となります。
何をもってオブジェクトの「内容」とするかで正しいかどうかが違ってきます。

例えば文字列オブジェクトの「内容」とは何でしょうか? やはり,「どんな文字がどう並んでいるか」ですよね,内容って。
そういう意味では,「文字列の内容を変えない破壊的メソッド」は存在します。
以下のコードを見ましょう。

str = "Ruby"

p str.frozen? # => false

str.freeze

p str.frozen? # => true

"Ruby" という文字列リテラルで文字列オブジェクトを生成し,ローカル変数 str に代入しました。
そのあと,そのオブジェクトが「凍結されているか」どうかを確認したところ,凍結されていないことが分かりました。
「凍結されている」というのは,オブジェクトに変化を与えることができない,という意味です。
次に,そのオブジェクトの freeze メソッドを呼びました。
このメソッドは,オブジェクトを凍結するメソッドです。
そのあと再び「凍結されているか」を確認すると,凍結されていました。

freeze メソッドによって文字列オブジェクトの「状態」が変化しました。つまり,freeze は破壊的メソッドです。
しかし,上述の意味での「文字列の内容」は変更していません。

こんなふうに,「オブジェクトの内容を変更しないがオブジェクトに変化を与える」メソッドは他にもあります。

ハッシュのデフォルト値を変更する Hash#default= なんかもそうですね。デフォルト値を変えたところで,要素(キー/バリューのペア)が変わるわけではありません。「存在しないキーでアクセスしたときの値」が変わるだけです。

これが,冒頭で掲げた言明を「適切な表現ではない」とする根拠です。

しかし,もちろん

ハッシュのデフォルト値も「内容」だ。オブジェクトの凍結状態も「内容」だ。

とする立場もあるでしょう。この場合,冒頭の言明は正しいことになります。しかし,少なくとも誤解を生じやすいとは言えるかと思います。私はああいう表現を避けますね。

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
3
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?