【问题标题】:Explicit specialization _of an inner-struct_ in non-namespace scope内部结构 _ 在非命名空间范围内的显式特化
【发布时间】:2013-05-06 14:35:27
【问题描述】:

我知道有很多关于“非命名空间范围内的显式专业化”的帖子;我已经阅读了其中的大部分内容,但是(除非我没有很好地理解答案)他们没有回答这个特定的问题。事实上,我在我的程序中找到了一种解决方法,但如果有的话,我很想知道这个问题的“真正解决方案”。

问题

请多多包涵,很难用语言表达。我有一个模板类A<typename T, unsigned n>。我想将类型检查器定义为模板内部结构is_A<typename U>,它检查U 是否为A。此结构按原样从std::false_type 继承,我将其专门用于从std::true_type 派生模板类型A<U,n>

我为什么要这样做?因为我想定义一个模板方法A::method<U>,当U 是一些A 或其他情况时,它的行为会有所不同。

什么有效

  1. is_a<U> 的非专门定义放在A 的声明之前。然后使用 2 个模板参数而不是 1 个来放置专用版本; template <> template <typename T, unsigned n> struct is_A< A<T,n> > : std::true_type {};。为什么不呢,但我不太喜欢添加模板参数,并且爆炸is_A 的定义也不是那么漂亮......
  2. 删除 is_A 并为 method 使用另一个类型检查器,它精确地描述了我期望的类型(ie,白名单方法而不是黑名单)。

除了这些变通方法之外,还有其他方法可以编写类似于以下标头的内容吗?

代码

这是我可以写的最小标题来重现错误:

#ifndef __EXAMPLE__
#define __EXAMPLE__

#include <type_traits>

namespace name
{


template <typename T, unsigned n>
class A
{
public:

    /**
     * Type checkers
     */
    template <typename U>
    struct is_A : public std::false_type {};

    template <> template <typename U>
    struct is_A< A<U,n> > : public std::true_type {};

    /**
     * Specialized method
     */

     // Version taking input of type A<U,n>
    template <typename U>
    void method( const A<U,n>& other ) {}

    // Version taking inputs of other types
    template <typename U,
    typename = typename std::enable_if< !is_A<U>::value >::type >
    void method( const U& x ) {}
};


}

#endif

这是我在编译包含此标头的 cpp 文件时遇到的错误:

.h:21:12: error: explicit specialization in non-namespace scope 'class name::A<T, n>'
.h:30:7: error: too many template-parameter-lists
.h:35:7: error: too many template-parameter-lists

【问题讨论】:

    标签: c++ c++11 template-specialization g++-4.7


    【解决方案1】:

    如果您按照编译器的建议进行操作,这似乎对我有用:省略 template&lt;&gt;

    template <typename U>
    struct is_A< A<U,n> > : public std::true_type {};
    

    【讨论】:

    • 你说得对,它也为我编译! :) 我不知道没有这个template&lt;&gt; 你可以专门化一个模板,你可以吗?
    • @Sh3ljohn 这是专门化模板类的正常语法,我实际上不明白你为什么要尝试额外的template&lt;&gt;
    • @Sh3ljohn 您发布的链接中的所有示例都没有使用template&lt;&gt; 和添加template&lt;...&gt; 来进行部分专业化AFAICT。 template&lt;&gt; 用于示例中的完全专业化。在某些(高级)案例中,您有两次 template&lt;...&gt;,但您的案例不是其中之一。
    • @Sh3ljohn 不客气。当您在模板类中专门化模板函数并在类外部提供定义时,您需要双模板语法。有关示例,请参阅 here
    猜你喜欢
    • 2011-08-12
    • 2018-09-17
    • 1970-01-01
    • 1970-01-01
    • 2011-03-04
    • 1970-01-01
    相关资源
    最近更新 更多