zoukankan      html  css  js  c++  java
  • C++——标准模板库

    1、泛型程序设计:将程序尽可能写的通用,将算法从特定的数据结构中抽象出来,成为通用的;C++模板为泛型程序设计奠定了关键的基础;STL是泛型程序设计的一个范例:容器container、迭代器iterator、算法algorithms和函数对象function object。

    2、命名空间namespace:一个命名空间将不同的标识符集合在一个命名作用域(named scope)中,是为了解决命名冲突。没有声明命名空间的标识符都处在无名的命名空间中。

    例如,声明一个命名空间NS:
    namspace NS {
    class File;
    void Fun ();
    }
    则引用标识符的方式如下,
    NS:: File obj;
    NS:: Fun ();

    可以利用using namespace std;指定在命名空间std中所有标识符都可以直接饮用,using NS::file;在当前作用域中就可以直接饮用file。

    在新的C++标准程序库中,所有标识符都声明在命名空间std中,头文件都不使用扩展名。

    3、容器:容器类是容纳、包含一组元素或元素集合的对象。异类容器类与同类容器类。还可以分为顺序容器与关联容器。七种基本容器:向量(vector)、双端队列(deque)、列表(list)、集合(set)、多重集合(multiset)、映射(map)和多重映射(multimap)

    容器的接口:外界可以使用的功能。包括方法函数和运算符。

    通用运算符:==,!=,>,>=,<,<=,=
    迭代方法begin(),end(),rbegin(),rend();访问方法size(),max_size(),swap(),empty()

    顺序容器:接口:插入方法 push_front(), push_back(), insert(), 运算符"="。

                     删除方法 pop(), erase(),clear()

                     迭代访问方法 使用迭代器

                     其他顺序容器访问方法(不修改的访问方法) front(),back(),下标运算符[]。

    顺序容器向量:向量属于顺序容器,用于容纳不定长的线性序列,提供对序列的快速随机访问,就是直接访问。向量是动态结构,它的大小不固定,可以在程序运行时增加或者减少。

    例子:求反问2~N中的质数,N在程序运行时由键盘输入。

    #include <iostream>
    #include <iomanip>
    #include <vector> //包含向量容器头文件
    using namespace std ;
    int main()
    {   
        vector<int>  A(10); // 用来存放质数的向量,初始状态有10个元素。
        int n; //质数范围的上限,运行时输入
        int primecount = 0, i, j;
        cout << "Enter a value >= 2 as upper limit for prime numbers: ";
        cin >> n;
        A[primecount++] = 2; // 2是一个质数
        for(i = 3; i < n; i++)
        {
            if (primecount == A.size()) // 如果质数表已满,则再申请10个元素的空间
                A.resize(primecount + 10);
            if (i % 2 == 0) //大于2的偶数不是质数,因此略过本次循环的后继部分
                continue;
            // 检查3,5,7,...,i/2是否i的因子
            j = 3;
            while (j <= i/2 && i % j != 0)
                j += 2;       

            if (j > i/2) // 若上述参数均不为i的因子,则i为质数
                A[primecount++] = i;
        }
        for (i = 0; i < primecount; i++) //输出质数
        {
            cout << setw(5) << A[i];
            if ((i+1) % 10 == 0) //每输出10个数换行一次
                cout << endl;
        }
        cout << endl;
    }

    4、适配器:适配器是一种接口类,为已有的类提供新的接口,目的是简化、约束,使之安全、隐藏或者改变被修改类提供的服务的集合。主要有三种适配器类型:容器适配器(用来扩展7中基本容器),迭代器适配器和函数对象适配器。

    5、迭代器:是面向对象版本的指针,提供了访问容器、序列中每个元素的方法

    输入迭代器
    可以用来从序列中读取数据
    输出迭代器
    允许向序列中写入数据
    前向迭代器
    既是输入迭代器又是输出迭代器,并且可以对序列进行单向的遍历
    双向迭代器
    与前向迭代器相似,但是在两个方向上都可以对数据遍历
    随机访问迭代器
    也是双向迭代器,但能够在序列中的任意两个位置之间进行跳转。
    6、算法:标准模板库中包括了70多个算法,其中包括了查找算法、排序算法、消除算法、计数算法、比较算法、变换算法、置换算法和容器管理等等

    算法是一种函数模板,可以分为

    不可变序列算法(non-mutating algorithms),不直接修改所操作的容器内容的算法
    可变序列算法(mutating algorithms),可以修改它们所操作的容器的元素。
    排序相关算法和数值算法
    例6-1,应用不可变序列算法对数据序列进行分析
    例6-2,以可变序列算法对数据序列进行复制,生成,删除,替换,倒序,旋转等可变性操作。
    例6-3,应用排序相关算法对序列进行各项操作
    例6-4,应用数值算法对数据序列进行操作

    //6-1.cpp
    #include <iostream>
    #include <algorithm>
    #include <functional>
    #include <vector>
    using namespace std;

    int main()
    {
     int iarray[]={0,1,2,3,4,5,6,6,6,7,8};
     vector<int> ivector(iarray,iarray+sizeof(iarray)/sizeof(int));
     int iarray1[]={6,6};
     vector<int> ivector1(iarray1,iarray1+sizeof(iarray1)/sizeof(int));  
     int iarray2[]={5,6};
     vector<int> ivector2(iarray2,iarray2+sizeof(iarray2)/sizeof(int));
     int iarray3[]={0,1,2,3,4,5,7,7,7,9,7};
     vector<int> ivector3(iarray3,iarray3+sizeof(iarray3)/sizeof(int));

     //找出ivector之中相邻元素值相等的第一个元素
     cout<<*adjacent_find(ivector.begin(),ivector.end())<<endl;

     //找出ivector之中元素值为6的元素个数
     cout<<count(ivector.begin(),ivector.end(),6)<<endl;

     //找出ivector之中小于7的元素个数
     cout<<count_if(ivector.begin(),ivector.end(),bind2nd(less<int>(),7))<<endl;

     //找出ivector之中元素值为4的第一个元素所在位置的元素
     cout<<*find(ivector.begin(),ivector.end(),4)<<endl;

     //找出ivector之中大于2的第一个元素所在位置的元素
     cout<<*find_if(ivector.begin(),ivector.end(),bind2nd(greater<int>(),2))
    <<endl;
     
     //找出ivector之中子序列ivector1所出现的最后一个位置,再往后3个位置的元素
     cout<<*(find_end(ivector.begin(),ivector.end(),ivector1.begin(),
    ivector1.end())+3)<<endl;

     //找出ivector之中子序列ivector1所出现的第一个位置,再往后3个位置的元素
     cout<<*(find_first_of(ivector.begin(),ivector.end(),ivector1.begin(),
    ivector1.end())+3)<<endl;
     
     //子序列ivector2在ivector中出现的起点位置元素
     cout<<*search(ivector.begin(),ivector.end(),ivector2.begin(),ivector2.end())
    <<endl;

     //查找连续出现3个6的起点位置元素
     cout<<*search_n(ivector.begin(),ivector.end(),3,6,equal_to<int>())<<endl;

     //判断两个区间ivector和ivector3相等否(0为假,1为真)
    cout << equal(ivector.begin(), ivector.end(), ivector3.begin()) << endl;

     //查找区间ivector3在ivector中不匹配点的位置
    pair<int*,int*>result=mismatch(ivector.begin(),ivector.end(),ivector3.begin());
    cout<< result.first - ivector.begin() << endl;
    }
    //6-2.cpp
    #include <iostream>
    #include <algorithm>
    #include <functional>
    #include <vector>
    using namespace std;

    class even_by_two{             //类定义形式的函数对象
    public:
     int operator()() const
     {return _x+=2;}
    private:
     static int _x;
    };
    int even_by_two::_x=0;       //静态数据成员初始化

    int main()
    {
     int iarray[]={0,1,2,3,4,5,6,6,6,7,8};
     int iarray1[]={0,1,2,3,4,4,5,5,6,6,6,6,6,7,8};
     vector<int> ivector(iarray,iarray+sizeof(iarray)/sizeof(int));
     vector<int> ivector1(iarray+6,iarray+8);  
     vector<int> ivector2(iarray1,iarray1+sizeof(iarray1)/sizeof(int));
     ostream_iterator< int > output( cout, " " );  //定义流迭代器用于输出数据
     
     //迭代遍历ivector1区间,对每一个元素进行even_by_two操作
        generate(ivector1.begin(),ivector1.end(),even_by_two());
     copy(ivector1.begin(),ivector1.end(),output);
     cout<<endl;

     //迭代遍历ivector的指定区间(起点和长度),对每一个元素进行even_by_two操作
        generate_n(ivector.begin(),3,even_by_two());
     copy(ivector.begin(),ivector.end(),output);
     cout<<endl;

     //删除元素6
        remove(ivector.begin(),ivector.end(),6);
     copy(ivector.begin(),ivector.end(),output);
     cout<<endl;
     
     //删除(实际并未从原序列中删除)元素6,结果置于另一个区间
        vector<int> ivector3(12);
     remove_copy(ivector.begin(),ivector.end(),ivector3.begin(),6);
     copy(ivector3.begin(),ivector3.end(),output);
     cout<<endl;

     //删除(实际并未从原序列中删除)小于6的元素
     remove_if(ivector.begin(),ivector.end(),bind2nd(less<int>(),6));
     copy(ivector.begin(),ivector.end(),output);
     cout<<endl;
     
     //删除(实际并未从原序列中删除)小于7的元素,结果置于另一个区间,
     remove_copy_if(ivector.begin(),ivector.end(),ivector3.begin(),
    bind2nd(less<int>(),7));
     copy(ivector3.begin(),ivector3.end(),output);
     cout<<endl;
     
     //将所有的元素值6,改为元素值3
     replace(ivector.begin(),ivector.end(),6,3);
     copy(ivector.begin(),ivector.end(),output);
     cout<<endl;
     
     //将所有的元素值3,改为元素值5,结果放置到另一个区间
     replace_copy(ivector.begin(),ivector.end(),ivector3.begin(),3,5);
     copy(ivector3.begin(),ivector3.end(),output);
     cout<<endl;
     
     //将所有小于5的元素值,改为元素值2
     replace_if(ivector.begin(),ivector.end(),bind2nd(less<int>(),5),2);
     copy(ivector.begin(),ivector.end(),output);
     cout<<endl;
     
     //将所有的元素值8,改为元素值9,结果放置到另一个区间
     replace_copy_if(ivector.begin(),ivector.end(),ivector3.begin(),
    bind2nd(equal_to<int>(),8),9);
     copy(ivector3.begin(),ivector3.end(),output);
     cout<<endl;
     
     //逆向重排每一个元素
     reverse(ivector.begin(),ivector.end());
     copy(ivector.begin(),ivector.end(),output);
     cout<<endl;
     
     //逆向重排每一个元素,结果置于另一个区间
     reverse_copy(ivector.begin(),ivector.end(),ivector3.begin());
     copy(ivector3.begin(),ivector3.end(),output);
     cout<<endl;
     
     //旋转(互换元素)[first,middle), 和[middle,end)
     rotate(ivector.begin(),ivector.begin()+4,ivector.end());
     copy(ivector.begin(),ivector.end(),output);
     cout<<endl;
     
     //旋转(互换元素)[first,middle], 和[middle,end],结果置于另一个区间,
     rotate_copy(ivector.begin(),ivector.begin()+5,ivector.end(),
    ivector3.begin());
     copy(ivector3.begin(),ivector3.end(),output);
     cout<<endl;
    }

    //6-3.cpp
    #include <iostream>
    #include <algorithm>
    #include <functional>
    #include <vector>
    using namespace std;

    int main()
    {
     int iarray[]={26,17,15,22,23,33,32,40};
     vector<int> ivector(iarray,iarray+sizeof(iarray)/sizeof(int));
     
     // 查找并输出最大、最小值元素
     cout<<*max_element(ivector.begin(),ivector.end())<<endl;
     cout<<*min_element(ivector.begin(),ivector.end())<<endl;

     //将ivector.begin()+4-ivector.begin()各元素排序,
     //放进[ivector.begin(),ivector.begin()+4]区间。剩余元素不保证维持原来相对次序
     partial_sort(ivector.begin(),ivector.begin()+3,ivector.end());
     copy(ivector.begin(),ivector.end(),ostream_iterator<int>(cout," "));
     cout<<endl;

     //局部排序并复制到别处
     vector<int> ivector1(5);
     partial_sort_copy(ivector.begin(),ivector.end(),ivector1.begin(),
    ivector1.end());
     copy(ivector1.begin(),ivector1.end(),ostream_iterator<int>(cout," "));
     cout<<endl;

     //排序,缺省为递增。
     sort(ivector.begin(),ivector.end());
     copy(ivector.begin(),ivector.end(),ostream_iterator<int>(cout," "));
     cout<<endl;

     //将指定元素插入到区间内不影响区间原来排序的最低、最高位置
     cout<<*lower_bound(ivector.begin(),ivector.end(),24)<<endl;
     cout<<*upper_bound(ivector.begin(),ivector.end(),24)<<endl;

     //对于有序区间,可以用二分查找方法寻找某个元素
        cout<<binary_search(ivector.begin(),ivector.end(),33)<<endl;
        cout<<binary_search(ivector.begin(),ivector.end(),34)<<endl;

     //下一个排列组合
     next_permutation(ivector.begin(),ivector.end());
     copy(ivector.begin(),ivector.end(),ostream_iterator<int>(cout," "));
     cout<<endl;

     //上一个排列组合
     prev_permutation(ivector.begin(),ivector.end());
     copy(ivector.begin(),ivector.end(),ostream_iterator<int>(cout," "));
     cout<<endl;

     //合并两个序列ivector和ivector1,并将结果放到ivector2中
     vector<int> ivector2(13);
     merge(ivector.begin(),ivector.end(),ivector1.begin(),ivector1.end(),
    ivector2.begin());
     copy(ivector2.begin(),ivector2.end(),ostream_iterator<int>(cout," "));
     cout<<endl;

     //将小于*(ivector.begin()+5)的元素放置在该元素之左
     //其余置于该元素之右。不保证维持原有的相对位置
     nth_element(ivector2.begin(),ivector2.begin()+5,ivector2.end());
     copy(ivector2.begin(),ivector2.end(),ostream_iterator<int>(cout," "));
     cout<<endl;

     //排序,并保持原来相对位置
     stable_sort(ivector2.begin(),ivector2.end());
     copy(ivector2.begin(),ivector2.end(),ostream_iterator<int>(cout," "));
     cout<<endl;

     //针对一个有序区间,找出其中一个子区间,其中每个元素都与某特定元素值相同
     pair<vector<int>::iterator,vector<int>::iterator> pairIte;
     pairIte=equal_range(ivector2.begin(),ivector2.end(),22);
     cout<<*(pairIte.first)<<endl;
     cout<<*(pairIte.second)<<endl;

     //合并两个有序序列,然后就地替换
     int iarray3[] = { 1, 3, 5, 7, 2, 4, 6, 8 };
     vector<int> ivector3(iarray3,iarray3+sizeof(iarray3)/sizeof(int));
     inplace_merge(ivector3.begin(), ivector3.begin()+ 4, ivector3.end());
     copy(ivector3.begin(),ivector3.end(), ostream_iterator<int>(cout, " ")); 
     cout<<endl;
     
     //以字典顺序比较序列ivector3和ivector4
     int iarray4[] = { 1, 3, 5, 7,1, 5, 9, 3 };
     vector<int> ivector4(iarray4,iarray4+sizeof(iarray4)/sizeof(int));
     cout<< lexicographical_compare(ivector3.begin(),ivector3.end(),
    ivector4.begin(),ivector4.end()) << endl;
    }
    //6-4.cpp
    #include <iostream>
    #include <numeric>
    #include <functional>
    #include <vector>
    using namespace std;

    int main()
    {
     int iarray[]={1,2,3,4,5};
     vector<int> ivector(iarray,iarray+sizeof(iarray)/sizeof(int));

     //元素的累计
     cout<<accumulate(ivector.begin(),ivector.end(),0)<<endl;
     //向量的内积
     cout<<inner_product(ivector.begin(),ivector.end(),ivector.begin(),10)<<endl;
     //向量容器中元素局部求和
     partial_sum(ivector.begin(),ivector.end(),ostream_iterator<int>(cout," "));
     cout<<endl;
     //向量容器中相邻元素的差值
     adjacent_difference(ivector.begin(),ivector.end(),
    ostream_iterator<int>(cout," "));
     cout<<endl;
    }
    7、函数对象:一个行为类似于函数的对象,它可以没有参数,也可以带有若干参数,其功能是获取一个值,或者改变操作的状态。任何普通的函数和任何重载了调用运算符operate()的类的对象都满足函数对象的特征,STL中也定义了一些标准的函数对象,如果以功能划分,可以分为算术运算、关系运算、逻辑运算三大类。为了调用这些标准函数对象,需要包含头文件<functional>。

  • 相关阅读:
    Windows2012 cannot access netapp CIFS share
    Import SHA2 SSL cert to Windows IIS7
    IE11登陆交行网银崩溃
    Understanding and Managing SMTP Virtual Servers
    IIS SMTP Queue stuck
    C#夯实基础之多线程三:线程的优先级
    C#夯实基础之多线程二:主线程、前台线程与后台线程
    ORA-00257: archiver error. Connect internal only, until freed.
    C#夯实基础之多线程一:初识多线程
    在Oracle中恢复被DROP掉的表
  • 原文地址:https://www.cnblogs.com/lemaden/p/10238077.html
Copyright © 2011-2022 走看看