1. 程式人生 > >C++之vector模板類

C++之vector模板類

    vector 稱為容器模板類,是同一種類型的物件的集合,每個物件都有一個對應的整數索引值。vector 不是一種資料型別,而只是一個類模板,可用來定義任意多種資料型別。vector 型別的每一種都指定了其儲存元素的型別,如vector<int> vector<string> 都是資料型別。vector是一個能夠存放任意型別的動態陣列,能夠增加和壓縮資料

初始化:

  1. int myarray[5] = {1,3,5,7,9};
  2. vector<int> ivec1(myarray , myarray+5);//數組元素值賦值給vector,深拷貝直接賦值
  3. vector<int> ivec2(ivec1);// ok: copy elements of ivec1 into ivec2 ,深拷貝
  4. vector<int> ivec3=ivec2;//ok,深拷貝 
  5. vector<string> svec(ivec1);// error: svec holds strings, not ints
  6. vector<int> ivec4(10, -1); // 10 elements, each initialized to -1
  7. vector<string> svec(10, "hi!");// 10 strings, each initialized to "hi!"
如果沒有給出元素的初始化式,則標準庫生成的初始值用於初始化容器中的每個元素。元素初始化式的值取決於儲存在 vector 中元素的資料型別。例如,int初始化為0,string初始化為0

注意: 

   ①vector 中的物件是沒有命名的,可以按 vector 中物件的位置來訪問它們。使用下標索引[]訪問,下標從0開始,且下標只能獲取已存在的元素

       使用size_type 型別時,必須指出該型別是在哪裡定義的。如vector<int>::size_type i

  1. for (vector<int>::size_type ix = 0; ix != ivec.size(); ++ix)    
  2.     ivec[ix] = 0;  

          迭代器訪問物件(推薦)

  1. vector<int>::iterator it;  
  2. for(it=vec.begin();it!=vec.end();it++)  
  3.     cout<<*it<<endl;  

1.常用函式列表

      push_back()------新物件插入到末尾
      insert()-------------插入一個元素或多個元素或一個內範圍元素至向量中的指定位置
      pop_back()--------刪除末尾元素      at()------------------返回對指定的索引物件的引用
      front()---------------返回最前面一個數據的引用
      back()---------------傳回最後一個數據的引用,故賦值時也應該是同類型的引用型別,若為空返回值不確定。      begin()--------------Returns a random-access iterator to the first element in the vector.
      end()----------------Returns the past-the-end iterator.
      data()----------------Returns a pointer to the first element in the vector.      assign()-------------清空vector並複製制定的元素到vector
      erase()--------------刪除指定的元素或者制定區間段的元素
      resize()--------------重定義size      clear()---------------移除容器中所有資料
      empty()--------------判斷容器是否為空,為空則為真。
  1. vector<int> v1,v2;  
  2. vector<int>::iterator c1_Iter;  
  3. v1.push_back(10);  
  4. v1.push_back(11);  
  5. v1.push_back(12);v1.push_back(13);  
  6. v1.push_back(14);  
  7. v1.pop_back();  
  8. int &a=v1.front();//引用
  9. int &b=v1.back( );//引用
  10. int &c= v1.at(0);//引用
  11. c1_Iter = c1.begin();//迭代器型別
  12. c1_Iter = c1.begin();//返回指向末尾元素的後一個的迭代器
  13. v2.assign(v1.begin(), v1.end());//v2=v1
  14. v2.assign({ 5, 6, 7 });//5,6,7依次push至末尾
  15. v2.assign(4,10);//v2=10 10 10 10
  16. v2.assign(v1.begin()+2, v1.begin()+4)//將v1索引2 3的元素賦給v2</span>    
  17. v1.erase( v1.begin( ) );//刪除索引0元素
  18. v1.erase( v1.begin( ) + 1, v1.begin( ) + 3 );//刪除索引1 2 3的元素
  19. v1.resize( 2,40 );  
  20. cout << "The size of v1 is " << v1.size( ) << endl;//輸出6
  21. cout << "The value of the last object is " << v1.back( ) << endl;//輸出40
  22. v1.resize( 10);  
  23. cout << "The size of v1 is now " << v1.size( ) << endl;//輸出10
  24. cout << "The value of the last object is now " << v1.back( ) << endl;//輸出0
  25. v1.insert( v1.begin( ) + 1, 88);//原索引1之前插入88
  26. v1.insert( v1.begin( ) + 2, 4, 50 );//原索引2之前插入4個50
  27. v1.insert( v1.begin( )+1, v1.begin( )+2, v1.begin( )+4 );//將原索引2,3的元素複製插入原索引1之前
  28. vector < vector <int> > vv1;// initialize a vector of vectors by moving v1
  29. vv1.insert( vv1.begin(), move( v1 ) );  
  30. if (vv1.size( ) != 0 && vv1[0].size( ) != 0 )  
  31.   {  
  32.     vector <int>::iterator Iter;  
  33.     cout << "vv1[0] =";  
  34.     for (Iter = vv1[0].begin( ); Iter != vv1[0].end( ); Iter++ )  
  35.         cout << " " << *Iter;  
  36.     cout << endl;  
  37.   }  
  38. v1.clear( );//清空vector

2.vector之結構體

    vector元素型別還可以是結構體,使用時注意結構體要定義為全域性。

  1. #include"stdafx.h" 
  2. #include<vector>  
  3. #include<iostream>  
  4. usingnamespace std;    
  5. typedefstruct rect    
  6. {    
  7.     int id;    
  8.     int length;    
  9.     int width;     
  10. }Rect;    
  11. int main()    
  12. {    
  13.     vector<Rect> vec;    
  14.     Rect rect={1,2,3};    
  15.     vec.push_back(rect);    
  16.     vector<Rect>::iterator it=vec.begin();    
  17.     cout<<(*it).id<<' '<<(*it).length<<' '<<(*it).width<<endl;  
  18.     return 0;  
  19. }     

3.vector之string

     vector<string>型別的快速初始化和輸出

  1. #include"stdafx.h" 
  2. #include<iostream>
  3. #include<vector> 
  4. #include"string"
  5. usingnamespace std;    
  6. int main()    
  7. {    
  8.     string   str[]={"hello""world""CHB","\n"};  
  9.     vector<string> strArray1(10,"hello");  
  10.     vector<string> strArray(str,str+sizeof(str)/sizeof(str[0]));  
  11.     for(vector<string>::iterator iter=strArray.begin();iter!=strArray.end();++iter)  
  12.         cout<<*iter<<endl;//換行符也被讀入  
  13.     for(vector<string>::size_type i=0;i<strArray1.size();i++)  
  14.         cout<<strArray1[i]<<endl;;  
  15.     return 0;  
  16. }  

4.作為引數或者返回型別

作為引數或者返回型別時。尊崇一般策略。比如,對於main()中的vector,子函式應該使用引用才能改變其值。例如任意數轉換為2進位制。如下

#include"iostream"
#include"vector"
using namespace std;
void Convert(vector<int> &ans,int number,int n)
{
        if(!number)return;
	else
	 {ans.push_back(number%n);
	  Convert(ans,number/n,n);}
}
void main()
{
	int number=121;
	vector<int> ans;
	Convert(ans,number,2);
	if(!ans.empty())
	   for(int it=ans.size()-1;it>=0;it--)
	      cout<<ans[it];
	cout<<endl;
}

5.Vector 變數之間的賦值

     直接使用賦值符號“=”賦值,建構函式()賦值,或者陣列賦值。均為深拷貝,即改變源vector元素的值不會對目標vector造成影響。如下所示;

void main()
{
    int myarray[5] = {1,3,5,7,9};
	vector<int>  v1(myarray , myarray+5);//深拷貝,指向地址不同
	vector<int>  v2 = v1,v3(v1);//深拷貝,指向地址不同
    myarray[0]=10;
	cout<<v1[0]<<" ";
	v1[2]=11;
    cout<<v2[2]<<" ";
	cout<<v3[2]<<" "<<endl;
 
	string s[3]={"we","love","china"};
    vector<string> s1(s,s+3);//深拷貝,指向地址不同
    vector<string> s2=s1,s3(s1);//深拷貝,指向地址不同
    s[0]="everyone";
	cout<<s1[0]<<endl;
	s1[2]="Hubei";
    cout<<s2[2]<<endl;
	cout<<s3[2]<<endl;

}
   輸出為:


6.結合Pair型別的使用

Pair型別概述

    pair是一種模板型別,其中包含兩個資料值,兩個資料的型別可以不同,基本的定義如下:

           pair<int, string> a;

    表示a中有兩個型別,第一個元素是int型的,第二個元素是string型別的,如果建立pair的時候沒有對其進行初始化,則呼叫預設建構函式對其初始化。直接對其初始化 pair<string, string> a("James", "Joy");

    由於pair型別的使用比較繁瑣,因為如果要定義多個形同的pair型別的時候,可以時候typedef簡化宣告:

             typedef pair<string, string> mypair;
             mypair pro("May", "Lily");
             mypair joye("James", "Joyce");

對於pair類,由於它只有兩個元素,分別名為first和second,因此直接使用普通的點操作符即可訪問其成員。

可以使用make_pair對已存在的兩個資料構造一個新的pair型別:

     int a = 8;
     string m = "James";
     pair<int, string> newone;
     newone = make_pair(a, m);
   簡單的程式碼如下:
#include "iostream"
#include"algorithm"
#include"vector"
#include"string"
using namespace std;
bool  strict_weak_ordering(const pair<int,std::string> a,   const pair<int, std::string>b)     
 { return   a.first < b.first;}       
  int   main()     
  {     
        using   namespace   std;     
        vector<pair<int,   string> >   vec;     
        vec.push_back(make_pair<int, string>(6, "ABC"));     
        vec.push_back(make_pair<int, string>(4, "BCD"));     
        vec.push_back(make_pair<int, string>(7, "EFG"));     
        sort(vec.begin(), vec.end(), strict_weak_ordering);
       for(  vector<pair<int,   string>>::iterator it =vec.begin(); it !=vec.end(); ++it)     
			cout<<it->second<<endl; 
	   return 0;
  }

7.附加

    #include<algorithm>中的泛函演算法

   搜尋演算法:find() 、search() 、count() 、find_if() 、search_if() 、count_if() 
   分類排序:sort()、merge() 
   刪除演算法:unique() 、remove() 
   生成和變異:generate() 、fill() 、transformation() 、copy() 
   關係演算法:equal() 、min() 、max()