模板分為模板函式和模板類。
模板是為了實現泛型程式設計,所謂泛型程式設計,就是指編寫與型別無關的**
比如以下的場景:
我們想在同乙份**裡實現交換整型,浮點型與字元型。
void swap(int& x, int& y)
void swap(double& x, double& y)
void swap(char& x, char& y)
此時,就意味著我得寫三份**,如何我要交換更多型別的資料呢?
所以,模板的好處就在此。
實現乙個交換的模板函式:
template t>
void swap(t& x,t& y)
但是,在實現了模板之後,編譯器是如何識別的?實際上,模板函式並沒有什麼實際的意義,而是由編譯器根據模板函式推演出函式的例項化,編譯器才能夠去呼叫該函式。
也就說是,我將引數傳遞給函式,編譯器會根據該型別去推演處乙份**,然後去呼叫該函式。
再去彙編中看看:
顯然這是兩個不同的位址,就說明這確實是兩個不同的函式,那麼也就是說編譯器去呼叫該**時,推演出了兩份例項化的**。
template
t>
class
vector
*/ delete _first;
}_first = tmp;
_finish = _first + size;
_endofstorage = _first + newcapacity;}}
public:
//預設成員函式
vector
() : _first(null)
, _finish(null)
, _endofstorage(null)
{}//v1=v2;
vector
(const
vector
& v)*/}
vector
& operator=(const
vector
& v)
~vector
()
_first = _finish = _endofstorage;
}void pushback
(consttx)
void popback
()
void insert
(size_t
pos, const
t& x)
//搬運
t* end = _finish - 1;
while (end >= _first + pos)
_first[pos] = x;
++_finish;
}void erase
(size_t
pos)
--_finish;
}size_t size
() const
size_t capacity
()
bool empty
()
t& operator(size_t
pos)
void resever
(size_t
size);
void resize
(size_t
size, const
t& value = t());
protected:
t* _first;
t* _finish;
t* _endofstorage;
};
實際上這個**中有乙個細節必須注意,在進行拷貝值時,會牽扯到深淺拷貝的問題。
比如上面這段**,在vs2013下是一定會崩掉的,原因是取決於編譯器對string的實現不同。
在除錯視窗觀察string:
可以看到string裡除了ptr還有乙個16位元組大小的buf,「aaa」就存在於buf中。
當擴容拷貝值時:
如果是上面那份**的情況:
可以看到,超長的字串buf已經村放不下了,那麼就會在記憶體中開闢空間來存放,ptr指向這段記憶體空間,拷貝時,將ptr也拷貝乙份,就會出現如下情況:
這樣看似好像也沒有問題,但是釋放空間就會出問題:
c 模板實現vector和list
h檔案 pragma once include include includeusing namespace std templateclass vector 拷貝構造 vector const vector v size v.size capacity v.capacity 賦值運算子的過載 ve...
C 模板實現Vector和雙向鍊錶
define crt secure no warnings 1 include include using namespace std template class vector vector size t n,const t data vector const vector v pdata new...
C 用模板實現順序表Vector
include以包含所需要的類檔案vector,還有一定要加上using namespace std。用模板寫函式或類都與型別無關,因此,stl中都是用模板實現容器,下面我們來介紹用模板實現順序表。pragma once include includeusing namespace std type...