• C++11范围for循环


    范围for循环:
    1.基于范围的for循环
    for(元素类型 元素对象:容器对象)
    {
      循环体
    }
    (1.1)如果循环体由单条语句或者单个结构块组成,可以省略花括号
    (1.2)用元素对象依次结合容器对象中的每一个元素,每结合一个元素,执行依次循环体,直至容器内的所有元素都被结合完为止.
    (1.3)不依赖于下标元素,通用
    (1.4)不需要访问迭代器,透明
    (1.5)不需要定义处理函数,简洁

    #include "stdafx.h"
    #include <iostream>
    #include <vector>
    #include <algorithm>
    using namespace std;
    void print(int i)
    {
        cout << i << " ";
    }
    
    int main()
    {
        int ai[]{ 65, 66, 67, 68, 69 };
        //计算数组元素个数
        size_t size = sizeof(ai) / sizeof(ai[0]);
        vector<int> vi(ai, ai + size);
        //基于下标运算的for循环,不是所有的容器都支持下标运算,不通用
        for (size_t i = 0; i < size; ++i)
            cout << ai[i] << " ";
        cout << endl;
        for (size_t i = 0; i < vi.size(); ++i)
            cout << vi[i] << " ";
        cout << endl;
        //基于迭代器的for循环,需要指明容器两端,且对迭代器做自增,必须了解迭代器的运算规则,不够透明
        for (int *it = ai; it != ai + size; ++it)
            cout << *it << " ";
        cout << endl;
        for (auto it = vi.begin(); it != vi.end(); ++it)
            cout << *it << " ";
        cout << endl;
        //基于泛型函数的for循环,需要提供针对元素的处理函数,对于一般性遍历而言比较繁琐
        for_each(ai, ai + size, print);
        cout << endl;
        for_each(vi.begin(), vi.end(), print);
        cout << endl;
        for (auto a : ai)
            cout << a << " ";
        cout << endl;
        for (auto a : vi)
            cout << a << " ";
        cout << endl;
        for (auto &a : ai)
            ++a;
        for (auto &a : vi)
            --a;
        for (auto const &a : ai)
            cout << a << " ";
        cout << endl;
        for (auto const &a : vi)
            cout << a << " ";
        cout << endl;
        for (char a : ai)
            cout << a << " ";
        cout << endl;
        for (char a : vi)
            cout << a << " ";
        cout << endl;
        return 0;
    }

    2.范围循环的注意事项
    (2.1)对map和multimap容器使用范围循环,每次拿到的元素既不是键也不是值,而是由键和值组成的pair
    (2.2)在使用基于范围的for循环时,不能违背容器本身的约束
    (2.3)基于范围的for循环,无论循环体执行多少次,冒号后面的表达式永远只执行一次
    (2.4)基于范围的for循环,其底层实现依然要借助于容器的迭代器,
    因此任何可能导致迭代器失效的结构性改变,都可能引发未定义的后果

    #include <iostream>
    #include <string>
    #include <map>
    #include <list>
    using namespace std;
    
    list<int> getScores(void)
    {
        cout << __FUNCTION__ << endl;
        return{ 70, 75, 80, 85, 90, 95 };
    }
    
    int main()
    {
        //对map和multimap容器使用范围循环,每次拿到的元素既不是键也不是值,而是由键和值组成的pair
        multimap<string, int> msi;
        msi.insert(make_pair("张飞", 100));
        msi.insert(make_pair("赵云", 90));
        msi.insert(make_pair("关羽", 80));
        for (auto c : msi)
            cout << c.first << ":" << c.second << endl;
        cout << endl;
        for (auto it = msi.begin(); it != msi.end(); ++it)
            cout << it->first << ":" << it->second << endl;
        cout << endl;
    
        //在使用基于范围的for循环时,不能违背容器本身的约束
        /*for (pair<string,int> &c:msi)
        if (c.first == "张飞")
        c.first = "张菲菲";*/
        for (auto c : msi)
            cout << c.first << ":" << c.second << endl;
        cout << endl;
        //基于范围的for循环,无论循环体执行多少次,冒号后面的表达式永远只执行一次
        for (auto score : getScores())
            cout << score << " ";
        cout << endl;
        auto scores = getScores();
        for (auto score : scores)
        {
            cout << score << " ";
            //基于范围的for循环,其底层实现依然要借助于容器的迭代器,
            //因此任何可能导致迭代器失效的结构性改变,都可能引发未定义的后果
            //scores.pop_front();
        }
        cout << endl;
        return 0;
    }

    3.使自己定义的容器类型支持范围循环
    一个类只要提供了分别获取起始和终止迭代器的begin和end函数,就可以支持基于范围的for循环

    #include "stdafx.h"
    #include <iostream>
    using namespace std;
    
    template <typename T, size_t S>
    class Array
    {
    public:
        T &operator[](size_t i)
        {
            return m_array[i];
        }
        T const &operator[](size_t i)const
        {
            return const_cast<Array&>(*this)[i];
        }
        //获取起始迭代器
        T *begin()
        {
            return m_array;
        }
        T const *begin()const
        {
            return const_cast<Array *>(this)->begin();
        }
        //获取终止迭代器
        T *end()
        {
            return m_array + S;
        }
        T const *end()const
        {
            return const_cast<Array *>(this)->end();
        }
    private:
        T m_array[S];
    };
    
    
    int main()
    {
        int i = 0;
        Array<int, 5> ai;
        for (auto &a : ai)
            a = ++i * 10;
        auto const &cai = ai;
        for (auto &a : cai)
            cout << /*++*/a << " ";
        cout << endl;
        return 0;
    }
  • 相关阅读:
    Android 获取当前系统时间
    Android下面的MD5加密
    产品管理有行业特殊性吗
    产品经理的人才模型
    什么样的人适合做产品经理
    产品经理是“通”才还是“专”才
    产品经理的职责都有哪些
    产品经理的知识结构是什么
    产品管理职位的级别都有哪些
    产品经理的职业发展路线是什么
  • 原文地址:https://www.cnblogs.com/LuckCoder/p/8467640.html
Copyright © 2020-2023  润新知