这为什么有效? (带有不同参数的模板类的模板友元函数)

时间:2014-07-21 18:23:28

标签: c++ templates friend

我有一个矩阵类:

template <typename T, const int N, const int M>
class TMatrixNxM
{
    (...)
    friend TMatrixNxM operator*(const TMatrixNxM&, const TMatrixNxM&);
    (...)
}

现在,在数学中,将NxM矩阵与MxP矩阵相乘会返回NxP矩阵。所以,我需要一个返回NxP矩阵的运算符,并将NxM和MxP矩阵作为参数,如下所示:

template <typename T, const int N, const int M, const int P>
TMatrixNxM<T, N, P> operator*(const TMatrixNxM<T, N, M> &par_value1, const TMatrixNxM<T, M, P> &par_value2)
{
    TMatrixNxM<T, N, P> result;

    (...) //Calculate

    return result;
}

当我测试时:

TMatrixNxM<float, 2, 3> m1;
(...) //Set the values

TMatrixNxM<float, 3, 4> m2;
(...) //Set the values

TMatrixNxM<float, 2, 4> m3 = m1 * m2;

m1.print(); //Matrix class has a print function for testing
printf("\n");
m2.print();
printf("\n");
m3.print();

就像这样。这究竟是如何以及为何有效? overloadad操作符需要一个额外的模板参数,而类只需要3,并且在声明中我没有指定任何内容。但是,如果我这样宣布:

template <typename T, const int N, const int M>
class TMatrixNxM
{
    (...)
    template<typename T, const int N, const int M, const int P> friend TMatrixNxM<N, P> operator*(const TMatrixNxM<N, M>&, const TMatrixNxM<M, P>&);
    (...)
}

然后编译器抱怨模板参数太少。我希望我不会错过这里明显的东西。

谢谢!

修改

我现在看到“太少争论”的抱怨是针对我不包括T的事实。应该是TMatrixNxM&lt; T,N,P&gt;等

1 个答案:

答案 0 :(得分:1)

两件事:

1)编译器理解类的模板参数与函数的模板参数之间的区别。你可以拥有一个包含3个模板参数的类,以及一个包含4个函数的函数。

所以当你宣布:

template <typename T, const int N, const int M, const int P>
TMatrixNxM<T, N, P> operator*(const TMatrixNxM<T, N, M> &par_value1, constXX TMatrixNxM<T, M, P> &par_value2)

您已经定义了一个带有4个模板参数的函数。然后,当编译器看到:

TMatrixNxM<float, 2, 4> m3 = m1 * m2;

编译器推导出4个模板参数:T,N,M和P.它推导出T = float,N = 2,M = 4,P =来自par_value2的第三个模板参数。

另请注意,函数的模板参数名称必须与类中的模板参数名称相同:

template <typename FOO, const int BAR, const int BAZ, const int QUX>
TMatrixNxM<FOO, BAR, QUX> operator*(const TMatrixNxM<FOO, BAR, BAZ> &par_value1, const TMatrixNxM<FOO, BAR, QUX> &par_value2)

2)在你的第二个例子中,你确实错过了一个模板参数。您正在尝试返回TMatrixNxM,但TMatrixNxM需要3个参数。如果您将返回类型更改为TMatrixNxM,它看起来会起作用...这就是您在第一部分中所做的。