将抽象类继承与实例化模板混合

时间:2014-08-01 04:23:23

标签: c++ templates inheritance

好的,我知道 - 主要是由于复杂性 - 不允许使用虚拟模板方法。

然而,考虑到这一点:

// something.h

class absClass
{
public:
    // ...
    // instead of templating the absClass fun method, define the different
    // overloads that are going to be used:
    virtual void fun(classA a) = 0;
    virtual void fun(classB b) = 0;
};

class impClass : public absClass
{
public:
    // ...
    template <typename T>
    void fun(T t)  
    { /* whatever */ }

    // declaration
    void fun(classA a);
    void fun(classB b);
};

然后我们在impClass中建立方法的特定实例化?

// something.cpp
#include "something.h"

// instantiation
void impClass::fun<classA>(classA t);
void impClass::fun<classB>(classB t);

这不应该起作用吗?我收到错误(无论是在.h还是.cpp中实例化)。

1 个答案:

答案 0 :(得分:1)

// ---- something.h
class absClass
{
public:
    // ...
    // instead of templating the absClass fun method, define the different
    // overloads that are going to be used:
    virtual void fun(classA a) = 0;
    virtual void fun(classB b) = 0;
};

class impClass : public absClass
{
public:
    // ...
    template <typename T>
    void fun(T t)  
    { 
        /* whatever */ #1
    }

    // declaration
    void fun(classA a)
    {
        // #2 -- the implementation of base class pure virtual function
        // Note: you must define this function, otherwise there is linker error
    }
    void fun(classB b)
    {
    }
};

//  ---- something.cpp
#include "something.h"

// instantiation
template void impClass::fun<classA>(classA t); // add missing "template"
template void impClass::fun<classB>(classB t); // add missing "template"

//  ---- main.cpp
impClass o;
classA a;
o.fun<classA>(a); // calls #1
o.fun(a); // calls #2

由于您正在编写void impClass::fun<classA>(classA t);,因此您正在进行专业化,因此您需要在其之前添加template<>

但这不是你实现虚函数的函数体,它们是其他的东西......检查我提供的两个不同的调用。


编辑#1,基于评论:

如果你想为特定的课程取得特殊成就,还有专业化的意义,对吗?

那么实例化的重点是什么呢?您是否尝试导出类模板?


编辑#2,基于评论:

这就是你想要的吗?

class impClass : public absClass
{
public:
    template <typename T>
    void so_fun(T t)  
    { 
        /* whatever */
        /* define the common behavior here */
    }
    void fun(classA a)
    {
        so_fun(a);
    }
    void fun(classB b)
    {
        so_fun(b);
    }
};

或:

template <typename T>
void so_fun(T t)  
{ 
    /* whatever */
    /* define the common behavior here */
}

class impClass : public absClass
{
public:
    void fun(classA a)
    {
        so_fun(a);
    }
    void fun(classB b)
    {
        so_fun(b);
    }
};