次のコードは g++ 4.4.5 で正常にコンパイルされますが、 g++ 4.5.3 でエラーが報告されます。変更されたのはコンパイラの動作ですか。もしそうなら、何が変わったのですか?
#include <iostream>
using namespace std;
class A
{
public:
A() {}
};
int main()
{
new A::A();
return 0;
}
次のコードは g++ 4.4.5 で正常にコンパイルされますが、 g++ 4.5.3 でエラーが報告されます。変更されたのはコンパイラの動作ですか。もしそうなら、何が変わったのですか?
#include <iostream>
using namespace std;
class A
{
public:
A() {}
};
int main()
{
new A::A();
return 0;
}
以前はなかったエラーが発生したため、明らかにコンパイラの動作が変更されました。
問題は、コンストラクターの呼び出しを修飾してはならない (つまり、型を前に付ける) べきではないということです。gcc 4.5.3 はこの問題を無視していたようですが、4.5.5 は標準の施行においてより厳格です。
編集:
これは C++98 では禁止されていた (しかし誰もが許可した) ことを覚えているようです。ただし、C++11 標準では、少なくとも特定の場所では明示的に受け入れています (§5.5.1/8 を参照)。gcc での C++11 のサポートを改善するときにバグが導入された可能性があります。逆に、C++11 標準が受け入れる場所でのみ許可されている可能性があります。少なくとも gcc 4.8.0は依然としてコードを拒否します。
奇妙なことに、一般的に厳密な Clang 3.2 は、警告なしでコードを受け入れます。
class-name::class-name 表記はコンストラクタとして定義されていますが、type-id ではありません。C++11 [5.3.1] の [expr.new] 定義で指定されたnewの要件。
new-expression:
::optnew new-placementopt **new-type-id** new-initializeropt
::optnew new-placementopt( **type-id** ) new-initializeropt