昨日も似たような質問をさせていただいたものです。
Rubyの定数探索について勉強しているのですが、全く理解できず困っています。
ruby
1## Code 1 2class A 3 CONST = "Hello, world" 4end 5 6class A::B 7 def method 8 CONST 9 end 10end 11 12p A::B.new.method # ruby.rb:7:in `method': uninitialized constant A::B::CONST (NameError)
以上のようなコードで、定数CONSTが参照できないのは何故でしょうか。
自分の考え
Rubyの定数探索は公式ドキュメントによると
定数参照時の定数の探索順序は、最初にネスト関係を外側に向かって探索し、次に継承関係を上位に向かって探索します。
とされています。Bクラスのメソッドmethod
が呼ばれたとき、Rubyは同クラス内には定数が定義されていないので、ネスト関係の外側を見に行くと思います。
クラスBは、クラスAの中のネストの中に定義したので(class A::B
)、クラスBの外側とはclass A
のはずです。クラスAは既に定数CONST
が定義されているので、これを参照することが出来るはず。
と考えてしまうのですが、実際にはruby.rb:7:in `method': uninitialized constant A::B::CONST (NameError)
というエラーが発生してしまいます。
一方、クラスBの定義の位置を以下のようにすると、参照が可能です。
ruby
1## Code 2 2class A 3 CONST = "Hello, world" 4 class B 5 def method 6 CONST 7 end 8 end 9end 10 11p A::B.new.method # "Hello, world"
class A::B
という定義をしたとき、Rubyでは実際に何が起こっているのでしょうか?Code2
のようにクラスAの中のネストにクラスBを定義させるということにはならないのでしょうか?
また
Rubyの定数探索はまず__レキシカルスコープ__を辿る
という言葉をどこかで聞いたのですが、__ レキシカルスコープ__ とは「Aの中に定義されたB」というCode1
のような関係(スコープ)のことは指さないのでしょうか?
昨日に引き続き質問を連投してしまい恐縮ですが、ご回答いただけると幸いです。
よろしくお願いいたします。なお、Rubyは2.1.0を使用しております。
回答3件
あなたの回答
tips
プレビュー
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
2019/12/06 22:44
2019/12/07 08:14 編集