Rubyにおけるインクリメント

2012-10-25 23:32:15

以前、rbenvをインストールしてから、
Rubyを勉強している。

といっても、
Railsちょっとやったり、
プログラミング言語 Rubyを読んだり、
WEBrickのソースを読んだりしてるだけで、
あまり何かを書いているわけではないが。

そんな中、今日初めて知ったことだが、
Rubyには、インクリメント演算子(++)がない。

a = 4
a++   # -> エラー
a+=1 # -> OK

へぇー、そうなんだ。

Rubyはまつもとゆきひろ(通称:Matz)がこだわって作ったオブジェクト指向言語だから、
何か理由があるんだろうなと思う。
ただ単純にないことより、そっちのほうが気になって調べてみた。

インクリメント演算子 - imHo
http://blade.nagaokaut.ac.jp/cgi-bin/scat.rb/ruby/ruby-list/126
Rubyにインクリメンタル演算子がない理由は?

まあ、当然Ruby界隈では何度も話されていることらしく、色々見つかった。

まとめると、

  1. Rubyは純粋オブジェクト指向言語である。
  2. インクリメント演算子++は、a++のように記述できるが、これは変数に対するメソッド呼び出し(正確にいうとメッセージを送信)にあたる。
  3. その場合、aがオブジェクトでなければならない。
  4. ここでいうaはFixnumオブジェクトなどの、同じ値は同じ参照を持ったオブジェクトなので、

a++とどこかに書くことで、その実行されている環境全ての同じ値の意味が変わってしまう。
たとえば、a == 1 ならば、a++とすることで、それ以降、実行環境内では1 == 2となってしまう。

ということだ。
1 == 2なんて、アンサイクロペディアじゃあるまいし。(笑)
参考:1=2

なるほど、理由は分かった。
しかも、上記のRubyにインクリメンタル演算子がない理由は?にもあるように、
Rubyの設計思想から、
「破壊的に見えるメソッドが Numeric などに実装されるのは、それがシンタックスシュガーといえどやはり整合性に欠け好ましくない」
というのも理解できた。

まあ、別にa++だろうが、a=+1だろうが、たいした違いだとは思わないしね。
っていうかRubyはループとかはほとんどeachだから、インクリメントすることなんてあまりなさそうだしね。

だけど、一つだけ疑問が。
a+=1 が、Rubyの内部で a = a + 1 と変換されるらしいけど、
これって、破壊的操作をNumericなどに実装していることにならないの?
Numericに実装はしていないのだとしたら、
a++ も同様に変換してしまえばいいのではないの?

うーん、構文解析などの他の理由がある気がする。
誰か教えてエロい人。というか、エロいRubyist。