與任何其他類相同,類模板可以聲明 static 成員:
template <typename T> class Foo { public: static std::size_t count() { return ctr; } void addctr() { ctr++; } void subctr() { ctr--; } private: static std::size_t ctr; // 下面可以有其他成員接口 }; template <typename T> std::size_t Foo<T>::ctr = 0; //定義並初始化 ctr
在這段代碼中,Foo是一個模板類,它有一個名為 count 的 public static 成員函數和一個名為 ctr 的 private static 數據成員。每個 Foo 的實例都有自己的 static 成員實例。即,對任意給定類型X,都有一個Foo<X>::ctr 和一個 Foo<X>::count() 成員函數。所有 Foo<X>類型的對象共享相同的 ctr 對象和 count 函數。例如:
//實例化 static 成員 Foo<string>::ctr 和 Foo<string>::count Foo<string> fs; //所有三個對象共享相同的 Foo<int>::ctr 和 Foo<int>::count 成員 Foo<int> fi, fi2, fi3;
與任何其他 static 數據成員相同,模板類的每個static 數據成員必須有且僅有一個定義。但是,類模板的每個實例都有一個獨有的 static 對象。因此,與定義模板的成員函數類似,我們將 static 數據成員也定義為模板:
template <typename T> std::size_t Foo<T>::ctr=0; //定義並初始化 ctr
與類模板的其他任何成員類似,定義的開始部分是模板的參數列表,隨后是我們定義的成員的類型和名字。與往常一樣,成員名包括成員的類名,對於從模板生成的類來說,類名包括模板實參。因此,當使用一個特定的模板參數類型實例化 Foo 時,將會為該類類型實例化一個獨立的 ctr ,並將其初始化為 0。
與非模板類的靜態成員相同,我們可以通過類類型對象來訪問一個類模板的 static 成員,也可以使用作用域運算符直接訪問成員。當然,為了通過類來直接訪問 static 成員,我們必須引用一個特定的實例。
運行示例:
#include<iostream> #include<vector> #include<string> using namespace std; template <typename T> class Foo { public: static std::size_t count() { return ctr; } void addctr() { ctr++; } void subctr() { ctr--; } private: static std::size_t ctr; // 下面可以有其他成員接口 }; template <typename T> std::size_t Foo<T>::ctr = 0; //定義並初始化 ctr int main(int argc, char* argv[]) { Foo<int>fi; cout << "fi.count()=" << fi.count() << endl; fi.addctr(); Foo<int>fi2; fi2.addctr(); cout << "fi2.count()=" << fi2.count() << endl; cout << "fi.count()=" << fi.count() << endl; cout << "Foo<int>::count()=" << Foo<int>::count() << endl; Foo<double>fd; cout << "fd.count()=" << fd.count() << endl; return 0; }
運行結果:
S:\ComputerTech\VS2015\ZhangSir_Proj\Console\Console\Debug>template.exe fi.count()=0 fi2.count()=2 fi.count()=2 Foo<int>::count()=2 fd.count()=0
類似任何其他成員函數,一個 static 成員函數只有在使用時才會實例化。