如何将模板实例传递给期望模板参数为基类的函数?

时间:2012-03-16 16:21:39

标签: c++ templates inheritance pointers

我不确定如何解释它,因为我真的不知道正确的术语,但这是一个例子:

template <typename T>
struct PointerWrapper {
    T *ptr;
};

struct Base {};

struct Derived : public Base {};

void test(PointerWrapper<Base>) {}

int main() {
    PointerWrapper<Derived> p;
    test(p);
    return 0;
}

由于“Derived”派生自“Base”,而“PointerWrapper”结构仅适用于指向模板指定类型的指针,因此没有任何问题。但是编译器抱怨道:

asdfg.cpp:15:11: error: could not convert ‘p’ from ‘PointerWrapper<Derived>’ to ‘PointerWrapper<Base>’

我甚至试过test(reinterpret_cast<PointerWrapper<Base>>(p)),但它说:

asdfg.cpp:15:51: error: invalid cast from type ‘PointerWrapper<Derived>’ to type ‘PointerWrapper<Base>’

那我该怎么办?

2 个答案:

答案 0 :(得分:1)

尽管PointerWrapper<Base>PointerWrapper<Derived>之间存在关联,但

BaseDerived的类型完全不同。

如果您想允许传入任何PointerWrapper<>,请执行以下操作:

template<typename T>
void test(PointerWrapper<T>)
{ }

如果您只想允许从PointerWrapper<T>派生T的{​​{1}}个实例,请执行以下操作:

Base

如果您使用的是C ++ 03,请将template<typename T> void test( PointerWrapper<T>, typename std::enable_if<std::is_base_of<Base, T>::value, void*>::type = 0 ) { } 替换为std::并删除boost::

答案 1 :(得分:1)

你可以这样做:

struct Base {};

struct Derived : Base {};

struct PointerWrapperBase {
    virtual Base* getBase() = 0;
};

template <typename T>
struct PointerWrapper : PointerWrapperBase {
    virtual Base* getBase() { return this->ptr; }
    T *ptr;
};

void test(PointerWrapperBase&) {}

int main() {
    PointerWrapper<Derived> p;
    test(p);
    return 0;
}