当前位置:编程学习 > C/C++ >>

C++11新特性:Range-based for loops

很多语言都有Range-based for loops这个功能,现在C++终于知道把这个重要功能加进语法中了。这个功能实在不知道该怎么翻译,语文没有学到家。

基本语法

[cpp] 
for ( range_declaration : range_expression) loop_statement       

比如说:
[cpp]
vector<int> vec; 
vec.push_back( 1 ); 
vec.push_back( 2 ); 
  
for (int i : vec ) 

    cout << i; 

for语言这么写可以很方便地遍历vector这类的容器。具体什么样的东西可以遍历呢?这个留在后面说。

对于比较复杂的容器可以用auto语句来简化类型声明

[cpp] 
map<string, string> complexVector; 
for ( auto complexVectorEntry : complexVector ) 

            cout << complexVectorEntry.first << " < " << complexVectorEntry.second << ">" << endl; 
}  


这两个例子中都没有修改遍历元素的值。如果你要想修改它们的值,请使用引用类型
[cpp] 
vector<int> vec; 
vec.push_back( 1 ); 
vec.push_back( 2 ); 
  
for (auto& i : vec ) 

   i++; 

请注意,你依然可以用continue语句来开始下一次迭代,使用break跳出循环。这一点和普通的for循环一样。

深入分析
[cpp] 
for ( range_declaration : range_expression) loop_statement       

“等价于”
[cpp] 

    auto && __range = range_expression ;  
    auto __begin = begin_expr(__range);  
    auto __end = end_expr(__range);  
    for (;__begin != __end; ++__begin) { 
        range_declaration = *__begin;  
        loop_statement  
    }  


请注意,“等价于”并不表示编译器就是这么实现range-based for loops的。只是说两者的运行效果等价
上面最重要的就是 begin_expr 和 end_expr 的定义如下:
对于数组类型 begin_expr和end_expr分别等于(__range)和(__range + __bound)
对于STL中的容器,两者分别等于__range.begin()和__range.end()
对于其他类型,两者分别等于begin(__range)和end(__range)。编译器将会通过参数类型来找到合适的begin和end函数
让自定义的类可以迭代

通过ranged-based for loops的等价语句可以看出,可以知道只要符合一定的要求,那么自己定义的类也可以放在ranged-based for loops中进行迭代。事实上要想进行迭代,一个类需要满足以下条件:
begin函数和end函数,作用是分别指向第一个数据和最后一个数据。返回值是一个可以自己定义的迭代器。既可以是成员函数,也可以是非成员函数。
迭代器本身支持* ++ !=运算符,既可以是成员函数,也可以是非成员函数。
比如说下面这个类:


[cpp] 
#include <iostream> 
  
using namespace std; 
  
 
class IntVector; 
  
class Iter 

    public: 
    Iter (const IntVector* p_vec, int pos) 
        : _pos( pos ) 
        , _p_vec( p_vec ) 
    { } 
  
    // these three methods form the basis of an iterator for use with 
    // a range-based for loop 
    bool 
    operator!= (const Iter& other) const 
    { 
        return _pos != other._pos; 
    } 
  
    // this method must be defined after the definition of IntVector 
    // since it needs to use it 
    int operator* () const; 
  
    const Iter& operator++ () 
    { 
        ++_pos; 
        return *this; 
    } 
  
    private: 
    int _pos; 
    const IntVector *_p_vec; 
}; 
  
class IntVector 

    public: 
    IntVector () 
    { 
    } 
  
    int get (int col) const 
    { 
        return _data[ col ]; 
    } 
    Iter begin () const 
    { 
        return Iter( this, 0 ); 
    } 
  
    Iter end () const 
    { 
        return Iter( this, 100 ); 
    } 
  
    void set (int index, int val) 
    { 
        _data[ index ] = val; 
    } 
  
    private: 
   int _data[ 100 ]; 
}; 
  
int 
Iter::operator* () const 

     return _p_vec->get( _pos ); 

  
 
int main() 
{   www.zzzyk.com
    IntVector v; 
    for ( int i = 0; i < 100; i++ ) 
    { 
        v.set( i , i ); 
    } 
    for ( int i : v ) { cout << i << endl; } 

补充:软件开发 , C++ ,
CopyRight © 2022 站长资源库 编程知识问答 zzzyk.com All Rights Reserved
部分文章来自网络,