次のコードが間違っているのはなぜですか? テンプレートはどのタイプのパラメーターを受け入れますか?
class MyClass
{
int var;
};
template <MyClass a> struct s
{
};
int main()
{
MyClass var;
struct s<var>;
return 0;
}
型以外のテンプレート パラメータは制約されており、すべてを使用できるわけではありません。特に、それらはコンパイル時の定数でなければなりませんが、これはあなたの場合ではありません。テンプレート定義に関して:
template <MyClass a> struct s
// ^^^^^^^
{
};
C++11 標準のパラグラフ 14.1/4 を参照してください。
タイプ以外のテンプレート パラメータには、次のいずれかの (オプションで cv 修飾された) タイプが必要です。
— 整数型または列挙型、
— オブジェクトへのポインタまたは関数へのポインタ
— オブジェクトへの左辺値参照または関数への左辺値参照、
— メンバーへのポインター、
— std::nullptr_t.
ご覧のとおり、ユーザー定義型は許可されていません。テンプレートのインスタンス化に関しては、次のようになります。
struct s<var>;
// ^^^ You most likely meant something like s<var> obj, but nevermind
C++11 標準のパラグラフ 14.3.2/1 を参照してください。
非型、非テンプレートのテンプレート パラメータのテンプレート引数は、次のいずれかになります。
— 整数型または列挙型の非型テンプレート パラメータの場合、テンプレート パラメータの型の変換された定数式 (5.19)。また
— 非型テンプレートパラメータの名前; また
— 静的記憶域期間と外部リンケージまたは内部リンケージを持つオブジェクトのアドレスを指定する定数式 (5.19)、または外部リンケージまたは内部リンケージを持つ関数 (関数テンプレートと関数テンプレート ID を含むが、非静的クラス メンバーを除く) で表される (ただし、名前が関数または配列を参照する場合は & を省略でき、対応するテンプレート パラメーターが参照の場合は省略しなければなりません。また
— null ポインター値に評価される定数式 (4.10)。また
— null メンバポインタ値に評価される定数式 (4.11); また
— 5.3.1 で説明されているように表現されたメンバーへのポインター。