【Ruby】"x = 1" は "x に 1 を代入する" ではない!
変数とはそもそも何なのか
という疑問から表題に行き着き、さらには
puts "Hello World" は "Hello World" つまり右に書いてあることを出力せよ!というものではないというところにまで行き着きました。
まぁ、わかりやすい話、puts は、右に書いてあるものを単に出力せよ!ということであるなら。適当な英数字を入れればそれら全て出力されるということである。
だが、実際に出力されるのは、数字ないしは文字列のみであり、変数は宣言されていない限り出力されない。
つまり、puts 〜 は、〜というオブジェクトを出力せよという命令文であり、オブジェクト以外はエラーとなる。
Ruby では全てオブジェクトであり、変数もオブジェクトである!
なんてなのは真っ赤な嘘だ!
ちなみに puts の右側に書けば、その時点でオブジェクトは生成されるっぽいので "Hello World" と書けば、その時点である id を持ったオブジェクトが生成され、出力される。
という仕組みのようである。
オブジェクトがその時点で生成されてなく、ただの英数字としての認識であるならば、宣言されていない変数も、出力されて然るべきなので、おそらく間違っていない。
ちなみに { } や [ ] もオブジェクトなので出力される。もちろん空なので表示自体は何もないのだが、エラーにはならない。
いちいち items = { } や、names = [ ] としなくても作れることは作れる。
items や names は変数だ。
では変数とは何なのかという問いに戻る。
そもそもオブジェクトを作るのに変数は必要ない。
puts でもオブジェクトは作成されたし、数字も"文字列"も入力されればオブジェクトとして生成される。(若干嘘あり。ある桁数までの数字は最初から id が割り振られている)
ただ、オブジェクトを扱うのに変数が必要なのである。
a = "aaa"
というのを見てみることにする。
この場合、生成されたオブジェクトは右辺の "aaa"である。
そして、変数 a はただの識別子である。それを見ていくためは、オブジェクトIDを調べてみれば良い。
a.object_id
=> 70187710432980
ここで
a = a + "aaa"
を見ていく。
仮に、 =が代入であるのであれば、変数 a のオブジェクトIDは変わらないはずである。変数は入れ物であるという説明を聞いたりもするが、中身が変わっただけで箱が変わらないというのであればIDが変わるのはおかしい。
a.object_id
=> 70187710384260
違いますね。
つまり、代入ではない。
=の右辺において、a + "aaa" という新しいオブジェクトが生成されたのである。
そのため、オブジェクトIDが変わった。変わったというより、違うものであるので違うIDが割り振られて当然なのである。
では変数とは何なのかという問いであるが
オブジェクトはバンバン作れる!が、作っただけではその場限りになってしまう。
そこで
オブジェクトを扱うために変数が存在している。
変数 = オブジェクト
は、あるオブジェクトをある一つの変数として扱い、いつでも使えるようにした。
ということである。
ようである。。。
まだまだ勉強浅いのでこの辺で。
余談ですが。数字にはもともとidが振られていると話しました。
0 は id = 1、1 は id = 3、2 は id = 5 ・・・
id = 2n + 1 のようです。
上限は
irb(main):008:0> 10000000000000.object_id
=> 20000000000001
irb(main):009:0> 100000000000000.object_id
=> 200000000000001
irb(main):010:0> 1000000000000000.object_id
=> 2000000000000001
irb(main):011:0> 10000000000000000.object_id
=> 20000000000000001
irb(main):012:0> 100000000000000000.object_id
=> 200000000000000001
irb(main):013:0> 1000000000000000000.object_id
=> 2000000000000000001
irb(main):014:0> 10000000000000000000.object_id
=> 70330865618720
このあたりのようです。