在定义一个模板类的时候,将类模板成员函数放在独立的cpp
实现文件中,将模板类声明放在一个h
文件中。在一个文件中需要使用到这个类,直接include
头文件发现出现链接错误。
由于模板不是函数,只是一些C++编译器指令,说明了如何生成类和成员函数定义,无法单独编译成obj
文件,因此不能将模板成员函数放在独立的实现文件中。模板必须与特定的模板实例化请求一起使用,最简单的方法是将所有的模板信息放在一个头文件中,并在要使用这些模板的文件中包含该头文件。
错误示例代码:
/*matrix.h*/
#ifndef _MATRIX_
#define _MATRIX_
#include <iostream>
#include <vector>
#include <assert.h>
template<typename T>
class Matrix {
int row, col;
std::vector<std::vector<T> > mem;
public:
Matrix();
~Matrix();
Matrix(T **arr, int n, int m);
void display();
};
#endif
/*matrix.cpp*/
#include "matrix.h"
template<typename T>
Matrix<T>::Matrix()
{
}
template<typename T>
Matrix<T>::~Matrix()
{
}
template<typename T>
Matrix<T>::Matrix(T **arr, int n, int m)
{
using std::vector;
assert(n >= 0 && m >= 0 && arr);
mem = vector<vector<T> >(n, vector<T>(m));
for (int i = 0; i < n; ++i)
for (int j = 0; j < m; ++j)
mem[i][j] = arr[i][j];
this->row = n;
this->col = m;
}
template<typename T>
void Matrix<T>::display()
{
for (auto &v: mem) {
for (auto &e: v)
std::cout << e << " ";
std::cout << "\n";
}
}
#include <iostream>
#include <vector>
#include <stdlib.h>
#include "matrix.h"
int * newIntRaw(int n)
{
return (int *)malloc(sizeof(int) * n);
}
int ** newMap(int n, int m)
{
int **pMap = (int **)malloc(sizeof(int *) * n);
for (int i = 0; i < n; ++i)
pMap[i] = (int *)malloc(sizeof(int) * m);
return pMap;
}
int main()
{
int row, col;
std::cin >> row >> col;
int **pMap = newMap(row, col);
// cut
Matrix<int> matrix(pMap, row, col); //链接错误,找不到函数实现
matrix.display();
// free map
return 0;
}
main: main.o matrix.o
g++ -std=c++11 main.o matrix.o -o main
main.o: main.cpp
g++ -std=c++11 -c main.cpp -o main.o
matrix.o: matrix.cpp
g++ -std=c++11 -c matrix.cpp -o matrix.o
clean:
rm *.o main
run:
./main
hui@hui-Lenovo-V1000:~/project/cpp$ make
g++ -std=c++11 -c main.cpp -o main.o
g++ -std=c++11 -c matrix.cpp -o matrix.o
g++ -std=c++11 main.o matrix.o -o main
main.o:在函数‘main’中:
main.cpp:(.text+0xe0):对‘Matrix::Matrix(int**, int, int)’未定义的引用
main.cpp:(.text+0xef):对‘Matrix::display()’未定义的引用
main.cpp:(.text+0x103):对‘Matrix::~Matrix()’未定义的引用
main.cpp:(.text+0x124):对‘Matrix::~Matrix()’未定义的引用
collect2: error: ld returned 1 exit status
Makefile:2: recipe for target ‘main’ failed
make: * [main] Error 1