調試了一下午,發現用C++寫模板方法真是有不少值得注意的地方,不是一般的麻煩,沒點經驗總結真是不行的。
首先,寫模板類(template class),這個在java叫作泛型類,需要注意幾點,在寫泛型類時.h頭文件和實現(.cpp)不能分離,也就是說,關於泛型類/模板類的所有邏輯都 要寫在一個文件中,我的做法是將類的函數體和函數原型都寫入頭文件,而省去.cpp的implement的文件。
頭文件如下:
#ifndef MOTHER_STUDENT_H
#define MOTHER_STUDENT_H
#include "Student.h"
#include <vector>
using namespace Member;
//下面是聲名
template<class T>
class MotherStudent:public Student{ //這里是繼承了一個父類(學生媽媽類繼承學生父類,該父類有個純虛函數void testVir() const),這個學生媽媽類擁有一個容器vector,裝着她生的學生孩子,呵呵)
private:
vector<T>* children; //成員函數,指針
public:
MotherStudent(){
this->children = new vector<T>();
std::cout << "這個媽媽創建了" << std::endl;
}
void setChildren(vector<T>&);
vector<T>& getChildren();
//該實現父類的純虛函數
void testVir(int a) const{
std::cout <<a <<std::endl;
}
};
//類定義體結束,下面是定義
template<class T>
void MotherStudent<T>::setChildren(vector<T>& children){
this->children = &children;
}
template<class T>
vector<T>& MotherStudent<T>::getChildren(){
std::cout << "這是來自於實現體的模版方法" << std::endl;
return *(this->children);
}
#endif
上面將這個模板類的頭文件寫完了,然后在main程序的文件中寫:
int _tmain(int argc, _TCHAR* argv[]){
MotherStudent<Student*> mother_std_obj;
MotherStudent<Student*>* mother_std = &mother_std_obj; //請注意這里的寫法,不能寫MotherStudent<Student>* mother_std = .. 因為C++中如果寫Student是抽象類(含純虛函數),這樣會尖括號中直接寫類名會用無參構造函數構造這個類的,然后報錯:“抽象類不能實例化”,所以這里用指針了。
vector<Student*> *children = new vector<Student*>();
for(int i = 0;i<4;i++){ //這個媽媽學生對象的children成員裝入四個CollegeStudent對象(該對象也是繼承自Student類的,所以可以裝入)
//這是int轉換成string的標准方法
stringstream strm;
strm<<i;
string name = "喬布斯" + strm.str()+"號";
//CollegeStudent構造函數2個參數,age和name
Student* per = new CollegeStudent(i,name); //因為模板類那里定義成了指針的,所以該模板類的T是Student*指針,所以里面的children成員變量也是包含指針的vector集合。
children->push_back(per);
}
mother_std->setChildren(*children); //setChildren方法的形參是定義成“引用”的了,所以這里傳入的是“解引用符號"解的指針。
for(vector<Student*>::iterator iter=mother_std->getChildren().begin();iter!=mother_std->getChildren().end();iter++){
//iter是得到"指向Student*的指針",所以(*iter)得到Student*,然后->name,訪問name
std::cout << "name is " <<(*iter)->name<< " age is " << (*iter) ->getAge() << std::endl;
}
}
最后,展示程序運行結果: