从递归模板类继承

时间:2015-12-13 01:28:01

标签: c++ templates inheritance recursion

由于递归模板,我正在尝试实现某种多维数组。

我的模板类具有以下结构:

template< typename T, unsigned int D >
class MultiArray
{
public:
    MultiArray();

protected:
    std::vector< MultiArray< T, D - 1 > > VecSubarrays;
};

template< typename T >
class MultiArray< T, 0 >
{
public:
    MultiArray();

protected:
    T Item;
};

使用一些存取器,修饰符等

我希望使用T = double“专门化”此模板类,并添加一些特定功能,例如运算符重载(+, - ,+ =, - =)。

所以我创建了这个模板类:

template< unsigned int D >
class MultiArrayDouble: public MultiArray< double, D >
{
public:
    MultiArrayDouble();

    template< unsigned int E >
        MultiArrayDouble< D >& operator+=(MultiArrayDouble< E > const& A_MAD);
    MultiArrayDouble< D >& operator+=(MultiArrayDouble< 0 > const& A_MAD);
};

我重载了operator+=(编辑:请参阅下面的实现)。

但是这种结构没有我期望的行为。我相信MultiArrayDouble< D >对象的子数组只是MultiArrayDouble< D - 1 >。但我递归编码operator+=,编译器说:

error: no match for 'operator+=' (operand types are 'MultiArray<double, 1u>' and 'const MultiArray<double, 1u>')

事实上,MultiArrayDouble< D >对象的子数组是MultiArray< double, D - 1 >,其中operator+=没有重载。

我认为我可以通过MultiArray< double, D >MultiArrayDouble< D >的某些演员来解决问题,但我正在寻找一个优雅的解决方案。

我以为我可以将子数组类型指定为模板参数,如:

template< typename T, unsigned int D, template< typename, unsigned int, typename > typename U >
class MultiArray
{
public:
    MultiArray();

protected:
    std::vector< U< T, D - 1, ??? > > VecSubarrays;
};

并将U替换为MultiArray以获取常规数组,或将MultiArrayDouble替换为双数组。但是我不能写出确切的子阵列类型(看看“???”)......

这个问题有标准解决方案吗?我应该避免从递归模板类继承吗?

谢谢。

修改

operator+=的实施:

template< unsigned int D >
template< unsigned int E >
MultiArrayDouble< D >& MultiArrayDouble< D >::operator+=(MultiArrayDouble< E > const& A_MAD)
{
    for (unsigned int i = 0 ; i < this->Length() ; i++)
    {
        (*this)[i] += A_MAD[i];
    }
    return (*this);
}

template< unsigned int D >
MultiArrayDouble< D >& MultiArrayDouble< D >::operator+=(MultiArrayDouble< 0 > const& A_MAD)
{
    for (unsigned int i = 0 ; i < this->Length() ; i++)
    {
        (*this)[i] += A_MAD;
    }
    return (*this);
}

template<  >
MultiArrayDouble< 0 >& MultiArrayDouble< 0 >::operator+=(MultiArrayDouble< 0 > const& A_MAD)
{
    (*this) += A_MAD;
    return (*this);
}

注意:

  • 运算符operator[](unsigned int i)返回第i个子数组,即VecSubarrays[i];
  • 我实施了从MultiArray< T, 0 >T&的隐式演员。

1 个答案:

答案 0 :(得分:0)

我宁愿使用模板规范机制,而不是继承自MultiArryDouble的特定类MultiArray。指定MultiArray<double, D>将是一种更好的方法。

一个缺点是你必须重复整个班级。

为什么不在operator+=中定义MultiArray?这样,将为定义T的每个operator+=定义它。如果你想要特定的行为,你可以使用静态助手类函数,在这里你可以为每种数据类型专门化操作符的行为。