0

これは私がやりたいことの擬似コードです。

template<typename T>
struct ConvertToT
{
    static_assert(false, "Explicit specialization for T required.");

    // Variant will be coerced to this type before calling Convert.
    std::uint32_t GetVariantType()
    {
        return VT_EMPTY;
    }
    T Convert(CComVariant& input)
    {
        return "ERROR!";
    }
};

template<>
struct ConvertToT<std::wstring>
{
    std::uint32_t GetVariantType()
    {
        return VT_BSTR;
    }
    T Convert(CComVariant& input)
    {
        return std::wstring(input.bstrVal, ::SysStringLen(input.bstrVal));
    }
};

/* repeat for several more explicit specializations:
 * template<>
 * struct ConvertToT<...>
 * {
 *     std::uint32_t GetVariantType()
 *     {
 *         return ...;
 *     }
 *     ... Convert(CComVariant& input)
 *     {
 *         return ...;
 *     }
 * };
 */

プライマリ テンプレートを無効にして、明示的な特殊化の使用を要求する方法はありますか?

4

3 に答える 3

6

はい、プライマリ テンプレートを定義しないでください。

template <typename> struct ConvertToT;

template <> struct ConvertToT<int>
{
    // ...
};

// etc.

静的アサーションが好きなら、ご想像のとおり、間接的なレベルが 1 つ追加されたコンパイル可能なコードを取得できます。

template <typename> struct never_true : std::false_type { };

template <typename T> struct Foo
{
    static_assert(never_true<T>::value, "Can't use this.");
};

これは、完全なタイプと不完全なタイプの両方で機能します。

( も使用できます!std::is_same<T, T>::value。)

于 2013-04-29T19:08:29.120 に答える
3

最も簡単な方法は、実装を提供しないことです。何かのようなもの:

template <typename T>
struct ConvertToT;

template<>
struct ConvertToT<SomeType>
{
    //  ...
};

等々。

于 2013-04-29T19:09:34.813 に答える
0

最初のアプローチをそのままにしておくことができますが、Boost で強化できます。

http://www.boost.org/doc/libs/1_36_0/libs/type_traits/doc/html/boost_typetraits/reference/is_class.html

template<typename T>
struct ConvertToT
{
    BOOST_STATIC_ASSERT_MSG(
    (boost::is_class<std::wstring, T>::value),
    "T must be of wstring type"
     );

    // Variant will be coerced to this type before calling Convert.
    std::uint32_t GetVariantType()
    {
        return VT_EMPTY;
    }
    T Convert(CComVariant& input)
    {
    return "ERROR!";
   }
};

または、C++11 を使用している場合は、std::is_class を使用します。

于 2013-04-29T19:22:09.300 に答える