一、C++11for循环的新用法
在C++98中,不同的STL容器和C风格数组的遍历方式各不相同,写法也不统一,而且不够简洁。而C++11基于范围的for循环可以简洁并且统一的方式遍历STL容器和C风格数组。
在介绍for循环新的语法之前,简单来看一下for循环之前遍历STL容器的例子:
#include<iostream>
#include<vector>
int main()
{
std::vector<int> vec = { 1,6,9,8,5,4,11 };
for (auto it = vec.begin(); it != vec.end(); it++)
{
std::cout << (*it) << " ";
}
return 0;
}
我们在遍历的过程中需要给出容器的两端:开头(begin)和结尾(end),但它不是基于范围来遍历的。在基于范围的for循环中,不需要给出开头和结尾的迭代器,直接抽取容器中的元素进行计算,使用这种方法可以让编码更简单。
C++98中for循环的语法格式:
for(init;expression;update)
{
//TODO(循环体内容)
}
注意:init指声明初始化的遍历的次数,expression限制初始值的数值,update更新初始值,也就是循环次数的累加。
C++11的for循环的语法格式:
for(declaration : expression)
{
//TODO(循环体)
}
注意:在上面的语法格式中 declaration 表示遍历声明,在遍历过程中,当前被遍历到的元素会被存储到声明的变量中。expression 是要遍历的对象,它可以是表达式、容器、数组、初始化列表等。
如下是C++11基于范围的for循环的例子:
#include<iostream>
#include<vector>
int main()
{
std::vector<int> vec = { 1,6,9,8,5,4,11 };
for (auto it : vec)
{
std::cout << it << " ";
}
return 0;
}
代码的测试结果如下:
在上面的例子中例子中,将STL容器的元素值拷贝到了it变量中,因此无法对容器的元素进行修改,如果要在遍历的过程中对容器元素进行修改,则需要通过引用(&)。
#include<iostream>
#include<vector>
int main()
{
std::vector<int> vec = { 1,6,9,8,5,4,11 };
for (auto &it : vec)
{
std::cout << it++ << " ";
}
std::cout << std::endl;
for (auto& it : vec)
{
std::cout << it << " ";
}
return 0;
}
代码的输出结果:
若在遍历容器的过程中,只是读取容器中的数值,可以使用const关键字,防止修改数据值,遍历时使用const auto&,这样相对于const auto效率高一些。
#include<iostream>
#include<vector>
int main()
{
std::vector<int> vec = { 1,6,9,8,5,4,11 };
for (const auto &it : vec)
{
std::cout << it << " ";
}
return 0;
}
代码的测试结果:
二、使用基于范围的for循环的其他细节
如下是遍历关联式容器map的测试代码:
#include<iostream>
#include<vector>
#include<map>
int main()
{
std::map<int, std::string>m1 = { {1,"naruto"},{2,"sakura"},{3,"luffy"} };
//C++98版本的for循环遍历map
for (std::map<int, std::string>::iterator it = m1.begin(); it != m1.end(); it++)
{
std::cout << "first:" << it->first << " second:" << it->second << std::endl;
}
std::cout << std::endl;
//C++11基于范围的for循环遍历map
for (const auto& it : m1)
{
std::cout << "first:" << it.first << " second:" << it.second << std::endl;
}
return 0;
}
测试代码的结果:
注意:使用普通的for循环遍历map时,通过迭代器遍历容器的各个元素,然后通过指针的方式访问first和second的值。而基于范围的for循环是通过对象的方式访问的容器元素。