目錄
一.指針的算術(shù)運算
二.了解Iterator(泛型指針)
三.所有容器的共通操作
四.使用順序性容器
五.使用泛型算法
六.設(shè)計泛型算法
七.map和set
八.使用iostream iterator
利用指針的算術(shù)運算完成find()函數(shù)的c++代碼:
#include#includeusing namespace std;
templateT1* find(const T1* first, const T1* last, const T2 value) //第一和第二個參數(shù)用于表示所搜索的容器范圍(兩個指針表示范圍),第三個參數(shù)為在容器中搜索的值。
{
if (!first || !last)
{
return 0;
}
for (; first != end; first++) //end指針所指的位置應(yīng)該是容器最后一個元素的下一個地址,這樣才可以保證容器中的所有元素都經(jīng)過了掃描
{
if (*first == value)
{
return first;
}
}
return 0;
}
int main()
{
int arr1[5] = { 5,3,10,9,6 };
int* p1 = find(arr1, arr1 + 5, 9); //第一個參數(shù)是容器的首地址,第二個參數(shù)是容器的最后一個元素的下一個地址,即為尾地址
if (p1 != (arr1 + 5))
{
cout<< "找到了,地址為:"<
知識點:
1.*(array+i) 與 array[i]的效果相同,下標操作就是將array的起始地址加上索引值,產(chǎn)出某個元素的地址,然后該地址再被提綱以返回元素值。
2.對于數(shù)組最后一個元素的下一個地址,只能對此地址進行比較,而不能用來讀取和寫入。
eg:
int ia[5] = {1,2,3,4,5};
int a1 = *(ia+6);//錯誤,對最后一個元素的下一個地址不能用來讀取和寫入
find(ia,ia+5,ia[3]);//正確,對最后一個元素的下一個元素可以用來比較
3.array數(shù)組不能為空,但是vector數(shù)組可以為空,同時vector類含有函數(shù)“ .empty "來判斷一個vector數(shù)組是否為空。
4.對于list容器,不適用于指針的算術(shù)運算,因為指針的算術(shù)運算必須首先假設(shè)所有元素都存儲在連續(xù)的空間里,但是list容器不存儲在連續(xù)的空間里,其每個節(jié)點都有三個值:front指向上一個節(jié)點,next指向下一個節(jié)點,value表示節(jié)點的值。
參考文章:C++ list(STL list)容器完全攻略(超級詳細) (biancheng.net)
5.list容器適用于存儲常需要修改(插入刪除操作)而不常讀取的數(shù)據(jù),而vector和array容器適用于存儲常讀取而不常修改(插入刪除操作)的數(shù)據(jù)。
二.了解Iterator(泛型指針)通過iterator指針實現(xiàn)find()函數(shù)的C++代碼:
#include#include#include#includeusing namespace std;
const int asize = 5;
templateIteratorType find1(IteratorType first, IteratorType last,const elemType value) //同理,第一個參數(shù)是容器的第一個元素的地址,而第二個參數(shù)是容器最后一個元素的下一個地址
{
for (; first != last; first++)
{
if (*first == value)
{
return first;
}
}
return last; //此地址只可以用來比較,而不能用來讀取和寫入
}
int main()
{
int ia[asize] = { 1,5,10,20,95 };
vectorivec(ia, ia + asize);
listilist(ia, ia + asize);
int* pia = find1(ia, ia + asize, 20);
if (pia != 0)
{
cout<< "找到了"<< endl;
}
vector::iterator iter1;
iter1 = find1(ivec.begin(), ivec.end(), 100);
if (iter1 != ivec.end())
{
cout<< "找到了"<< endl;
}
list::iterator iter2;
iter2 = find1(ilist.begin(), ilist.end(), 95);
if (iter2 != ilist.end())
{
cout<< "找到了"<< endl;
}
system("pause");
return 0;
}
支持兩種形式:一對指針或是一對指向某種容器的iterator
知識點:
1.對于不同類型的iterator指針,其運算符進行的操作是根據(jù)iterator class內(nèi)相關(guān)的inline函數(shù)提供的。
eg:
//first是一個iterator泛型指針
first++;
//如果first是vector的泛型指針,則first++則是將目前的地址加上一個元素的大小。
//如果first是list的泛型指針,則first++則是會沿著list的指針前進到下一個元素。
2.每個標準容器都提供有一個begin()的操作函數(shù),可返回一個iterator指向第一個元素, 也提供一個end()的操作函數(shù)指向最后一個元素的下一位置。
3.定義iterator:需要提供兩個參數(shù)
(1).迭代對象(即為某個容器)的類型,用來決定如果訪問下一元素。
(2).iterator所指的元素類型,可以決定iterator提領(lǐng)操作的返回值。
//iteratoriter1;
//iteratoriter2;
//實際語法:
vector::iterator iter1;
list::iterator iter2;
4.const_iterator:只可讀而不可進行其他操作
vector::const_iterator iter;
5.通過iterator指針訪問容器內(nèi)的操作:間接訪問( ->)
vector::iterator iter;
int size = iter->size();
三.所有容器的共通操作①." == " 和 "!="運算符,返回true或false。
②."="運算符,將某個容器復(fù)制給另一個容器。
③.empty()會在容器無任何元素時返回true,否則返回false。
④.size()返回容器內(nèi)目前持有的元素個數(shù)。
⑤.clear()刪除所有元素。
⑥.begin()返回一個iterator指向容器的第一個元素,end()返回一個iterator指向容器的最后一個元素的下一位置。
⑦.insert()將單一或某個范圍內(nèi)的元素插入容器內(nèi),erase()將容器內(nèi)的單一元素或者某個范圍內(nèi)的元素刪除。
四.使用順序性容器1.順序容器用來維護一組排列有序、類型相同的元素。
2.順序性容器種類:
①.vector:以一塊連續(xù)內(nèi)存來存放元素,其中的每個元素都被存儲在距離起始點的固定偏移位置上,隨機訪問效率較高,而對于任意位置的插入或刪除操作缺乏效率。
②.list:以雙向鏈接而非連續(xù)內(nèi)存來存儲內(nèi)容,對于任意位置的插入或刪除操作都頗具效率,但是隨機訪問操作則效率不高。(存放元素的內(nèi)存不連續(xù),因此不支持iterator的偏移運算)
③.deque:以連續(xù)內(nèi)存來存放元素,與vector類似,但同時對于最前端和最后端元素的插入、刪除操作效率更高。
3.定義順序性容器方法:
①.產(chǎn)生空容器:
listslist;
vectorivec;
②.產(chǎn)生特定大小的容器,每個元素都以其默認值作為初值。(eg.int和double類型的默認值為0)
vectorivec(10);
listilist(20);
③.產(chǎn)生特定大小的容器,并為每個元素指定初值。
vectorivec(1024,10);
listilist(10,5.20);
④.通過一對iterator產(chǎn)生容器。這對iterator用來標示一整組作為初值的元素的范圍。
int ia[5] = {1,2,3,4,5};
vectorivec(ia,ia+5);
listilist(ia,ia+5);
⑤.根據(jù)某個容器產(chǎn)出新容器。復(fù)制原容器內(nèi)的元素,作為新容器的初值。
listilist1;
listilist2(ilist1);
4.三種順序性容器都有push_back()和pop_back()函數(shù),但只有l(wèi)ist和deque容器擁有push_front()和pop_front()函數(shù)。
5.insert函數(shù)的變形函數(shù)(除push_front()和push_back()外)
①.
iterator insert(ierator position,elemType value);
將value值插入position之前,同時會返回一個iterator指向被插入的元素。
②.
void insert(iterator position,int count,elemType value);
在position前插入count個元素,這些元素的值都和value的相同。
③.
void insert(iterator position,iterator2 first,iterator2 last);
可在position之前插入[first,last)所標示的各個元素。
④.
iterator insert(iterator position);
在position之前插入元素,元素的初值為其所屬屬性的默認值。
6.erase()函數(shù)的變形函數(shù)(除pop_front()和pop_back()外)
①.
iterator erase(iterator position);
刪除position所指的元素。
②.
iterator erase(iterator first,iterator last);
刪除[first,last)范圍內(nèi)的元素。
五.使用泛型算法1.使用泛型算法需要包含對應(yīng)的頭文件"algorithm";
#include
2.常用泛型搜索算法:
①.find()用于搜索無序集合中是否存在某值。搜索范圍由iterator[first,last)標出。如果找到目標, find()會返回一個iterator指向該值,否則返回一個iterator指向last。
iterator find(iterator first, iterator last, elemType value);
②.binary_search()用于有序集合的搜索。如果搜索到目標則返回true,否則返回false。binary_search比find()更有效率。
bool binary_search(containerTypename, elemType value);
③.count()返回數(shù)值相符的元素數(shù)目。
④.search()比對某個容器內(nèi)是否存在某個子序列。例如給定序列{1,3,5,7,2,9},如果搜索子序列{5,7,2},則search()會返回一個iterator指向子序列起始處。如果子序列不存在,就返回一個iterator指向容器末尾。
3.取得數(shù)列大元素值:max_element()。將一對iterator傳給max_element(),它會返回該范圍內(nèi)的大值。
elemType max_element(iterator first,iterator last);
4.復(fù)制容器:copy()。將一對iterator傳給copy()標示出復(fù)制范圍,第三個iterator指向復(fù)制行為的目的地。
void copy(iterator1 first,iterator1 last,iterator2 begin);
六.設(shè)計泛型算法泛型算法filiter()的C++代碼:
#include//#include//使用function objectL less#include#include ///使用泛型算法find_if()
using namespace std;
templateOutputIterator filter(InputIterator first, InputIterator last, OutputIterator at, const ElemType& value, comp pred) //參數(shù)分別為傳入容器的范圍,傳入容器的首地址,用于比較的值,比較類型函數(shù)
{
while ((first = find_if(first, last, bind2nd(pred, value))) != last)
{
cout<< "found value: "<< *first<< endl;
//將過濾后的數(shù)據(jù)放到新的容器,同時更新相應(yīng)位置:
*at++ = *first++;
}
}
int main()
{
const int elem_size = 8;
int is[ elem_size ] = { 12,8,43,0,66,21,3,7 };
vectorivec(elem_size);
cout<< "過濾數(shù)組中小于8的值:"<< endl;
filter(is, is + elem_size, ivec.begin(), elem_size,less());
system("pause");
return 0;
}
知識點:
1.若要使用事先定義的function object,需包含頭文件:#inclucde
(visual studio 2022中已無法打開源文件
其中包括:
①.六個算術(shù)運算:plus
②.六個關(guān)系運算:less
③.三個邏輯運算,分別對應(yīng)&&、||、!:logical_and
2.適配器adapter:
①.binder adapter:使binary(二元)fuction object轉(zhuǎn)化為unary(一元)fuction object。
(1).bind1st:將指定值綁定至第一操作數(shù)。
bind1st(less,val);
//相當于: val<
(2).bind2nd:將指定值綁定至第二操作數(shù)。
bind2nd(less,val);
//相當于
②.negator adapter:對function object的真?zhèn)沃等》础?/p>
(1).not1可對unary function object的真?zhèn)沃等》础?/p>
not1(bind2nd(less,value));
//小于取反得到大于或等于
(2).not2可對binary function object的真?zhèn)沃等》础?/p>
③.insertion adapter: 使用需要包含頭文件
不能在array上使用,因為array不支持元素插入操作
可以對為設(shè)置大小的容器進行插入操作,但不能進行賦值操作
(1).back_inserter()會以容器的push_back()函數(shù)取代assignment運算符,參數(shù)為復(fù)制的目標容器。
(2).inserter()會以容器的insert()函數(shù)取代assignment運算符,接受兩個參數(shù),一個是復(fù)制的目標容器,另外一個是iterator指向容器內(nèi)的插入操作起點。
(3).front_inserter()會以容器的push_front()函數(shù)取代assignment運算符,參數(shù)為復(fù)制的目標容器。同時這個inserter只適用于list和deque。
filter(ivec.begin(),ivec.end(),back_inserter(ivec2),elem_size,greater);
//第三個參數(shù)從最初的ivec2變?yōu)榱薭ack_inserter(ivec2)
//此操作使push_back()函數(shù)替代assignment運算符將元素復(fù)制到ivec2容器中
七.map和set1.使用map和set分別需要包含頭文件
2.使用map:
(1).map被定義為一對數(shù)值:
mapmapname;
其中的key通常是個字符串,扮演索引的角色,value則是key對應(yīng)的值。
(2).map有兩個member,分別為first指向key,second指向value:
mapm1;
map::const_iterator it = m1.begin();
it->first; //key
it->second; //value
(3).查詢某個map內(nèi)是否存在某個key:
①.把key當作索引使用:
int count = 0 ;
if(!(count = words["vermeer"]));
原理:若map中不存在某個key,則會將此key放到map中并獲得默認值0。
②.通過map的find()函數(shù):
map::iterator::it = words.find("vermeer");
原理:如果key在map中,則會返回一個iterator指向key/map形成的一個pair,如果key不在map中則會返回end()。
③.通過map的count()函數(shù):
if(words.count("vermeer"));
原理:count()函數(shù)返回key項在map內(nèi)的個數(shù)。
3.使用set
(1).set由一群key組合而成:
setiset;
(2).set的insert()函數(shù):
①加入單一元素:使用單一參數(shù)的insert():
iset.insert(ival);
②加入某個范圍的元素,使用雙參數(shù)的insert():
iset.insert(vec.begin(),vec.end());
(3).set元素皆依據(jù)其所屬類型默認的less-than(遞增)運算符進行排列。
4.任何一個key在map和set中最多只會有一份,如果需要儲存多份相同的key值,則必須使用multimap和multiset。
八.使用iostream iterator#include#include//istream_iterator, ostream_iterator
#include //copy(),sort()
#include#includeusing namespace std;
int main()
{
istream_iteratoris(cin); //first
istream_iteratoreof; //end
vectortext;
//輸入:
cout<< "輸入:"<< endl;
copy(is, eof, back_inserter(text));
sort(text.begin(), text.end());
ostream_iteratoros(cout, " ");
//輸出:
cout<< "輸出:"<< endl;
copy(text.begin(), text.end(), os);
system("pause");
return 0;
}
知識點:
1.包含頭文件
2.需要提供一對iterator:first和last用來表示元素范圍:
指定istream對象即為first
不指定istream對象即為end-of-file
istream_iteratoris(cin); --- first; //指定istream對象即為first
istream_iteratoreof; --- last; //不指定istream對象即為end-of-file
3.創(chuàng)建ostream_iterator來標示字符串元素的輸出位置:
ostream_iteratoros(cout," "):
第二個參數(shù)可以是C-style字符串,也可以是字符串常量,用來表示各個元素被輸出時之間的分隔符。
4.使用copy()來進行輸入和輸出:
輸入:
copy(is,eof,back_inserter(text));
輸出:
copy(text.begin(),text.end(),os)
5.使用iostream_iterator完成從文件中讀取,寫到文件中去:
將istream_iterator綁定至ifstream object,并將ostream_iterator綁定至ofstream object。
ifstream in_file("input_file.txt");
ofstream out_file("output_file.txt");
istream_iteratoris(in_file); //first;
istream_iteratoreof; // last;
ostream_iteratoros(out_file," ");
你是否還在尋找穩(wěn)定的海外服務(wù)器提供商?創(chuàng)新互聯(lián)www.cdcxhl.cn海外機房具備T級流量清洗系統(tǒng)配攻擊溯源,準確流量調(diào)度確保服務(wù)器高可用性,企業(yè)級服務(wù)器適合批量采購,新人活動首月15元起,快前往官網(wǎng)查看詳情吧
網(wǎng)站標題:泛型編程風(fēng)格-創(chuàng)新互聯(lián)
標題路徑:http://jinyejixie.com/article42/icsec.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供網(wǎng)站設(shè)計、靜態(tài)網(wǎng)站、網(wǎng)站維護、企業(yè)網(wǎng)站制作、云服務(wù)器、虛擬主機
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網(wǎng)站立場,如需處理請聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時需注明來源: 創(chuàng)新互聯(lián)
猜你還喜歡下面的內(nèi)容