c++ - 如何告诉模板参数是从某个类派生的

标签 c++ templates

现在,我正在使用基于特征的方法编写程序。除了基本框架之外,每个功能都作为自己的包出现,派生自要素类。

我有以下 header 定义:

class Feature
{
    public:
        Feature(std::string Name)
            : Parent(nullptr), Name(Name)
        {
            if (FeatureNames.count(Name) == 0)
                FeatureNames.insert(Name);
            else
                throw std::logic_error(std::string("Feature: The Feature with the name '") + Name + "' already exists");

        }


        virtual ~Feature(){}

        const std::string &getName(){ return Name; }
        virtual void shutDown() = 0;

    protected:
        Feature *Parent;

    private:
        static std::set<std::string> FeatureNames;
        std::string Name;
};

template<class ChildFeat>
class FeatureEx : public Feature
{
    public:
        FeatureEx(std::string Name) :Feature(Name){}
        virtual ~FeatureEx(){}
        void addChildFeature(ChildFeat *Child);

    protected:
        std::vector<ChildFeat*> Children;
};

//implementation
template<class ChildFeat>
void FeatureEx<ChildFeat>::addChildFeature(ChildFeat *child)
{
    Children.push_back(child);
    child->Parent = this;
}

我有一个 Feat-class 和一个 ChildFeat-Class,如下所示:

class FeatureClass : public FeatureEx<MyChildFeatureInterface>
{
    ...
}

class MyChildFeat : public Feature, public MyChildFeatureInterface
{
     ...
}

当我现在尝试在 FeatureClass 的实例上调用 addChildFeature() 方法时 编译器哭了,因为 addChildFeat() 方法只看到一个 MyChildFeatureInterface,当然没有成员 Parent

我可以通过直接从 Feature 派生 MyChildFeatureInterface 轻松绕过这个问题,但一方面我发现这不是最优的,另一方面我想知道是否有一种方法可以告诉编译器:“这个模板参数可以是任何类,但它必须派生自类 X”。

最佳答案

当然,您可以轻松地告诉编译器一个类必须派生自 Base。

函数示例:

template<class X> auto my_function1(X&& x)
-> decltype(*declval<const volatile Base**>() = &x, declval<void>());

如果 x 不是 Base 的一种,所以不是从它派生的,赋值是错误的,因此函数在重载时从考虑中移除-解决步骤。
我喜欢这种形式,因为它可以立即转移到检查您可能需要的任何奇怪表达式

或者像 Matthieu M. 一样正确地使用标准库中的预打包测试 mentions in a comment (仅在类里面工作):

template<class X> auto my_function2(X&& x)
-> enable_if_t<is_base_of<Base, typename decay<X>::type>::value, void>;

关于c++ - 如何告诉模板参数是从某个类派生的,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25265127/

相关文章:

c++ - 在查找::之前的名称时,函数模板的名称是否应该可见?

wpf - 如何通过绑定(bind)将 RowDefinition 或 ColumnDefinition 动态添加到 Grid?

java - 线路问题拆分

c++ - 作为重载运算符的函数包装器

c++ - 获取网络接口(interface)信息C++

templates - Go 模板示例

C++ 将派生类作为基类模板参数传递

c++ - 字符串流是如何工作的?

java - 如何使用 JNI 在 C++ 中返回 java 字符串

c++ - fwprintf 正在打印垃圾