【问题标题】:declaring a template method for a template class为模板类声明模板方法
【发布时间】:2017-05-28 14:38:12
【问题描述】:

我正在尝试在模板类上声明一个模板方法,但它对我不起作用。 最好通过给出代码来解释,所以这里是: 我有这门课:

矩阵.h

template <class T,int a,int b>
class Matrix {
private:
   int x;
   int y;
public:
   class IllegalOperation();
   template<T,int c,int d>
   Matrix<T,a,b> operator+(const Matrix<T,c,d> m);
   //...
}

矩阵.cpp

template<class T,int a,int b>
template<T,int c,int d>
Matrix<T,a,b> Matrix<T,a,b>::operator+(const Matrix<T,c,d> m){
  if(a!=c || b!=d) throw IllegalOperation();
  // add matrices and return the result
}

我希望此代码适用于任何 2 种类型的 Matrix 和 Matrix,其中 a、b、c 和 d 可以不同。 例如,我希望这段代码编译并返回错误(在运行时):

const Matrix<int, 3, 2> m1;
const Matrix<int, 7, 3> m2;
// init m1 and m2
m1+m2;

虽然这段代码应该编译并成功运行:

const Matrix<int, 3, 2> m1;
const Matrix<int, 3, 2> m2;
// init m1 and m2
m1+m2;

但是,当我尝试编译上面的代码时,我得到了这个错误:

在 m1+m2 中不匹配 âoperator+

【问题讨论】:

  • 您希望operator+ 能够仅添加相同大小的矩阵,但使用Matrix&lt;T, c, d&gt; 作为其参数会自相矛盾,其中c 和@ 987654329@ 可能不分别等于ab
  • 除了你目前遇到的那个错误,你应该知道stackoverflow.com/questions/495021/…
  • @ForceBru 我并没有自相矛盾,但我希望在运行时而不是在编译时显示错误。我希望代码编译然后给我错误。
  • “我希望在运行时而不是在编译时显示错误”然后不要将矩阵大小作为模板参数。
  • @Loay " 我认为在我的情况下是分离实现。" 好吧,那根本行不通:-P

标签: c++ templates matrix


【解决方案1】:

把你的代码改成这个(不考虑我认为这里可能有问题的地方,只是为了让它编译)

#include <type_traits>

template <typename T,int a,int b>
class Matrix {
public:
    template<typename T2, int c, int d>
    Matrix<T,a,b> operator+(const Matrix<T2, c, d>& m) const;
private:
    int x;
    int y;
};

template <typename T,int a,int b>
template <typename T2, int c, int d>
Matrix<T, a, b> Matrix<T, a, b>::operator+(const Matrix<T2, c, d>&) const {
    if(a != c || b != d) {
        throw IllegalOperation{};
    }
    /*constexpr*/ if (!std::is_same<T, T2>::value) {
        throw Error{};
    }
    return *this;
}

int main() {
    const Matrix<int, 3, 2> m1{};
    const Matrix<int, 7, 3> m2{};
    m1 + m2;
    return 0;
}

我在这里做了一些改变

  1. operator+const,您试图在 const 对象上调用非 const 成员函数,但不起作用
  2. 加法运算符中的矩阵参数现在被引用了
  3. operator+不能在cmets中提到的.cpp文件中定义,必须放在头文件中(如果要拆分接口和实现,最好是In the C++ Boost libraries, why is there a ".ipp" extension on some header files )
  4. 我通常喜欢首先使用public 部分,因为它可以让读者更好地了解类的接口。

【讨论】:

  • 当T和T2是不同类型时你会怎么做?
  • @n.m.你的意思是operator+ 成员?你能澄清一下吗?
  • 是的,例如,当您添加Matrix&lt;int,2,2&gt;Matrix&lt;double,2,2&gt; 时会发生什么?返回*this 会编译,但实际添加呢?
  • @n.m. ¯_(ツ)_/¯ OP 在编译代码时遇到了问题,所以这就是我修复的问题。但我可以想象一个合适的场景,例如,如果你有intshort。如果 OP 想要更通用,他们稍后将不得不向该模板添加约束。
  • @Loay 你检查一下,但你应该这样做当且仅当这在作业中明确说明。否则,从内部模板中完全删除 T2 参数。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2011-10-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-03-23
  • 1970-01-01
  • 2017-02-09
相关资源
最近更新 更多