クラス定義があるとします:
class CustomClass {
int member;
};
次の変数定義が正しくコンパイルおよび動作するのはなぜですか。
CustomClass CustomClass; // the variable is properly constructed
これはコンパイラを混乱させ、エラーを表示させるべきではありませんか?
クラス定義があるとします:
class CustomClass {
int member;
};
次の変数定義が正しくコンパイルおよび動作するのはなぜですか。
CustomClass CustomClass; // the variable is properly constructed
これはコンパイラを混乱させ、エラーを表示させるべきではありませんか?
クラス名と変数名は、2 つの別個の名前空間を占有します。コンパイラは、最初CustomClass
が型で、2 番目CustomClass
が変数名であることを理解できます。
要求された疑いは、必ずしも C++ の大文字と小文字を区別するモードに関するものではなく、上記で定義されたクラスと同じ名前を持つ変数宣言です。あなたのC++コンパイラは、解析しているトークンのタイプを推測するのに十分賢いと思います..
私はそれを機能させるコンパイラの魔法だと思います。これは理想的にはコンパイラエラーであるべきだということに同意します(少なくとも私を混乱させます)。
あなたが次のようなことをしようとすると
#include <iostream>
class Test { public: int member; };
Test Test; // comaeu warns 'expression has no effect!'
Test.member = 10; // dosen't compile!
int main(){
Test Test;
Test.member = 10; // compiles fine after global 'Test's are commented!!
std::cout<<Test.member<<std::endl;
return 0;
}
グローバルスコープでの「Test.member」の使用はコンパイルされませんが、両方のグローバル「Test」がコメント化された後、「main()」内で同じように機能します。
C ++にはプログラマーを興奮させるのに十分な複雑さがありますが、コンパイラーも貢献しているのはどうですか:-)?
この回答は、C++ でこれを実行できる主な理由を間接的に示しています。これは C との下位互換性に帰着します。C では、型は異なる名前空間を持っていたため、型とオブジェクト、または型と関数を同じ名前で宣言することができました。
C と互換性を持たせるために、C++ は、オブジェクトまたは関数が型の宣言を隠蔽できるようにするいくつかの特別な規則を追加しました。