未定义的部分专用类方法的引用

时间:2015-06-27 18:27:44

标签: c++ templates specialization partial-specialization

我一直在研究一组代表各种几何形状的模板类,我意识到我希望能够专门化各种类来处理引用和指针,例如。

template<typename T>
class rect{ // as in rectangle
public:
  point<T> point1, point2; // Point simply contains two instances of type T
  ...    // Twenty functions or so follow
};

template<typename T>
class rect<point<T>>{ // trying to put a point in a point makes no sense anyway
public:               // so I see this technique as valid
  point<T>& point1,& point2;
  ...    // I really don't want to redefine them if I don't have to
};

问题始于我的测试程序

#include <iostream>
#include <TGeometry.hpp>

template<typename T>
class test{
public:
  T A;

  void myfunc(){std::cout << "from base\n";}
  void otherfunc(T O);
  test(const T nA) : A(nA) {}
  test(){}
};

template<typename T>
void test<T>::otherfunc(T O){A += O;}

template<typename T>
class test<T&>{
public:
  T& A;

  void myfunc(){std::cout << "from refr\n";}
  void otherfunc(T O); // Shouldn't this default to using test<T>::otherfunc?
  test(T& nA) : A(nA) {}
};


int main(){ using std::cout;
  using namespace d2;

  test<int> Atest(5);
  test<int&> Btest(Atest.A);

  Atest.myfunc(), Btest.myfunc();
  Btest.otherfunc(Atest.A); // test<T&>::otherfunc undefined?
  Atest.otherfunc(10);

  std::cin.ignore();
  return 0;
}

此程序在Mingw_w64中编译,以

退出
C:\Users\*>g++ -o test.exe quicktest.cpp -I .\Libraries
C:\Users\THEMAG~1\AppData\Local\Temp\ccszH6xM.o:quicktest.cpp:(.text+0x42):undefined reference to `A<char, 2>::f()'
collect2.exe: error: ld returned 1 exit status

这可能只是我缺乏知识,但this网站(在底部,部分特化成员下的第一个例子)暗示你可以排除部分特化的功能定义,只要正如您所声明的那样,它将默认使用主模板的定义。

能够做到这一点可以节省我几天的工作,因为我不必重新定义我班级的所有功能。所以我的问题是,是什么让我的代码不能编译,并且我可以/如何将我的类专门用于引用(我仍然需要为指针做这些)而不必重新定义它们的函数?这仅仅是改变代码必须如何工作的引用问题,例如如果使用了函数,那么主要特化的函数就会移动引用。

1 个答案:

答案 0 :(得分:0)

我不认为专业类模板从非专用类模板继承方法实现的概念是正确的。考虑例如std :: enable_if。此类的全部内容是通过引用模板的特定版本中不存在的类型来触发子类失败。如果您描述的行为是正确的,那么这将无效。或者至少,您需要使用两个特化而不是泛型和一个特化来定义enable_if(事实并非如此)。

我认为这是一个“XY”的情况:你希望能够做某事,但我认为你更有可能修改你的设计,所以你不需要做那件事。我可以想象获得通用模板成员函数会有用的情况,但它应该是相对罕见的,并且这不会让我成为其中一种情况。

更有可能的是,如果你的模板的重点是将类型T放在一个点上,并且将一个点放在一个点上没有意义,那么你应该静态断言T本身不是某种Point模板类。专业化为您提供了哪些额外功能?为什么需要引用/指针专门化?