修复算术类中的循环依赖

时间:2015-07-24 15:23:07

标签: c++ templates c++11 circular-dependency crtp

我有一组实现奇怪的重复模板模式的类。但是,诀窍是基类需要返回子类的实例。这是一个例子:

template <typename SubType>
class ArithmeticBase
{
public:
    template <typename OtherType>
    const Addition operator+(const OtherType &other)
        {return Addition(get_subclass(), other);}

    // ...
    // Operators for subtraction, multiplication, division, ...

private:
    const SubType &get_subclass() const
        {return *static_cast<const SubType*>(this);}
};

template <typename OperatorType1, typename OperatorType2>
class Addition : ArithmeticBase<Addition<OperatorType1, OperatorType2>>
{
public:
    Addition(const OperatorType1 &op1, const OperatorType2 &op2)
        : op1(op1)
        , op2(op2)
    {}

private:
    const OperatorType1 &op1;
    const OperatorType2 &op2;
};

// ...
// Additional classes for subtraction, multiplication, division, ...

编译失败是因为Addition类在ArithmeticBase类中使用之前未定义:

arithmetic.cpp:6:8: error: unknown type name 'Addition'
        const Addition operator+(const OtherType &other)
              ^

我该如何解决这个问题?

3 个答案:

答案 0 :(得分:4)

您可以在基类之前转发声明Addition

template <typename OperatorType1, typename OperatorType2>
class Addition;
template <typename SubType>
class ArithmeticBase
{
...
};

这允许编译器知道在定义之前存在类型Addition

答案 1 :(得分:2)

或使用$window之后声明的非会员表格:

Addition

答案 2 :(得分:1)

除了向前声明Addition课程(如bhzag的答案所示)之外,您还需要将operator+的定义移到定义Addition类之后。否则,您将在下一行收到错误。

确保定义位于头文件中。如果不是,那么您将收到链接器错误。