2016-11-15 3 views
4

は、次のコードを考えてみます。テンプレート特殊は

struct X 
{ 
    template <typename T> 
    class Y 
    {}; 
}; 
template<> 
class X::Y<double>{ 
}; 

ここでは、double型のためのYクラスを特化していると、コードが正常に動作します。いずれかが、私はこのケースでは、クラスYを特化することができます方法を知っている

'X::Y': explicit specialization is using partial specialization syntax, use template <> instead!

用量:

template<typename A> 
struct X 
{ 
    template <typename T> 
    class Y 
    {}; 
}; 
template<typename A> 
class X<A>::Y<double>{ 
}; 

は、コンパイラがエラーを報告します。問題は、私はこれにコードを変更した場合ということですか?

+0

は、エラーメッセージが助けていないと言う何をしていますか? 'template 'の代わりに 'template <>'をネストされたテンプレートの特殊化に使用してください。 –

+0

それは働かない!私もこれに疲れました: テンプレート<> クラスX :: Y { }; – MEMS

答えて

2

簡単な答え - テンプレート化された外部クラスの内部クラスを完全に専門化することはできません。しかし、あなたが本当に同様の効果を実現したい場合は、ダミーの不履行テンプレートパラメータに部分的な特殊化を試みることができるに:

#include <iostream> 

template<typename A> 
struct X 
{ 
    template <typename T, T* =nullptr> 
    class Y{}; 
}; 

template<typename A> 
template<double *Ptr> 
class X<A>::Y<double, Ptr> { 
public: 
    static constexpr int value = 1; 
}; 

int main() { 
    std::cout << X<int>::Y<double>::value << std::endl; 
} 

[live demo]

+1

ブック:古典のC++の高度なメタプログラミング、33ページの言う: テンプレート特殊は、名前空間レベルで有効です。 構造体のX { テンプレート クラスY {}; テンプレート<> //違法ですが、通常はコンパイラによって許容されます クラスY {}; }; テンプレート<> //法律 クラスX :: Y { }; あなたがしたことはうまくいくかもしれませんが、必ずしもそうではありません! – MEMS

+0

@MEMSあなたは正しいかもしれません。標準の例を探した後、私は '[temp.class.spec]/5'を実際には過剰解釈しているかもしれないことに気付きました。 C++標準コア言語のアクティブな問題に基づいてコード –

+1

@MEMSを更新しています。クラス内の明示的な特殊化 'インラインの部分的なメンバークラスの特化はうまく形成されています...私の前のコードは本当に有効でした。 [参照](http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_active.html#727) –

3

外側のテンプレートクラスを明示的に特殊化することなく、内側のテンプレートクラスを特殊化することはできません。 See this question for more details and a quote from the standard.

回避策:X内側に詳細名前空間にTAの両方をとる外部クラスを作成し、別名:

namespace impl 
{ 
    template <typename A, typename T> 
    struct Y { }; 
} 

template<typename A> 
struct X 
{ 
    template <typename T> 
    using Y = impl::Y<A, T>; 
}; 

明示的に内側との両方を専門と罰金している場合外部クラスの場合は、次の構文を使用できます。

template <> 
template <> 
class X<int>::Y<double> 
{ 
    // ... 
}; 

Example on wandbox

+0

具体的なXとYのように特殊化したい場合: テンプレート<> クラスX :: Y { }; この場合もそれは文句を言う!それは言う:エラーC2992: 'X :: Y ':無効またはテンプレートのパラメータリストがありません – MEMS

+0

@MEMS:あなたは二倍の 'テンプレート<>'が必要です。 [ワンドボックスの例](http://melpon.org/wandbox/permlink/5QsXzayEWYB8Vz1E) –

+0

私の答えも更新されました。 –

関連する問題