GCC 4.0:模板函数中“没有匹配的函数调用”

时间:2009-02-03 15:06:05

标签: c++ templates gcc

我想知道为什么以下设计的示例代码在Visual Studio 2005中完美运行,但在GCC中生成错误(“调用Interpolate()时没有匹配的函数调用”,如下所示)。

另外,我该如何解决这个问题?似乎错误消息只是一个通用消息,因为GCC没有针对问题的实际原因的更具体的消息,它必须输出一些东西。对于如何在没有一些非常丑陋的解决方法的情况下继续移植这个类,我有点不知所措。

namespace Geo
{
    template <class T>
    class TMyPointTemplate
    {
        T X,Y;
    public:
        inline TMyPointTemplate(): X(0), Y(0) {}
        inline TMyPointTemplate(T _X,T _Y): X(_X), Y(_Y) {}
        inline T GetX ()const { return X; }
        inline T GetY ()const { return Y; }
        //...
        template<T> TMyPointTemplate<T> Interpolate(const TMyPointTemplate<T> &OtherPoint)const
        {
            return TMyPointTemplate((X+OtherPoint.GetX())/2,(Y+OtherPoint.GetY())/2);
        }           
    };
    typedef TMyPointTemplate<int> IntegerPoint;
}

Geo::IntegerPoint Point1(0,0);
Geo::IntegerPoint Point2(10,10);
Geo::IntegerPoint Point3=Point1.Interpolate(Point2); //GCC PRODUCES ERROR: no matching function for call to 'Geo::TMyPointTemplate<int>::Interpolate(Geo::IntegerPoint&)'

感谢您的帮助,

阿德里安

2 个答案:

答案 0 :(得分:9)

我认为在函数定义中根本不需要模板,因为它是与类一起内联定义的

TMyPointTemplate Interpolate(const TMyPointTemplate &OtherPoint)const {

应该这样做。

当你使用模板来定义非内联函数时,我认为你需要像这样的class关键字。

template<class T> // <- here
TMyPointTemplate<T> TMyPointTemplate<T>::Interpolate(const TMyPointTemplate<T> &OtherPoint)const {

答案 1 :(得分:9)

Evan的answer解决了这个问题,但我认为解释原因可能有用。

如上所述,Interpolate是一个成员模板函数,带有一个未命名的“非类型模板参数”(而不是类型模板参数,几乎可以肯定你的意图)。为了表明这一点,我们可以为该参数命名:

template<T t> TMyPointTemplate<T> Interpolate
      (const TMyPointTemplate<T> &OtherPoint)const

我们现在可以看到如何调用该函数,我们只需要为't'提供一个值:

Geo::IntegerPoint Point3=Point1.Interpolate <0> (Point2);

在此处“T”之前添加 typename ,会将其声明为类型模板参数。但是,仅进行该更改将导致错误,因为标识符“T”已用于封闭类模板中的模板参数名称。我们必须更改成员函数模板的模板参数的名称:

template <class T>
class TMyPointTemplate
{
public:
  //...
  template<class S> TMyPointTemplate<T> Interpolate
                 (const TMyPointTemplate<S> &OtherPoint) const
  {
    return ...;
  }                       
};