c++如何使用std::for_each_c++容器算法遍历详解【总结】

胖芳吖_5749

胖芳吖_5749

2026-02-13

243人浏览

原创

c++oding="utf-8" ?>

std::for_each 无法用 const_iterator 遍历并修改元素,因 const_iterator 解引用得 const T&,而 lambda 若声明 int& 参数则绑定失败;只读遍历时用普通迭代器配值参或 const 引用参数即可。

c++如何使用std::for_each_c++容器算法遍历详解【总结】

std::for_each 为什么遍历不了 vector 的 const_iterator?

因为 std::for_each 默认要求迭代器可解引用并赋值(即非 const),而你传了 cbegin()/cend() 或手动写了 const_iterator,却在 lambda 里试图修改元素——编译器会直接报错:assignment of read-only location。

实际场景中,多数人想「只读遍历」,但误以为必须用 const 迭代器才能安全;其实只要 lambda 参数是 const T& 或值类型,用普通 begin()/end() 完全没问题,且更兼容。

  • 正确写法:std::for_each(v.begin(), v.end(), [](int x) { /* 只读用 x */ });
  • 错误写法:std::for_each(v.cbegin(), v.cend(), [](int& x) { x = 0; }); —— x 是 const int&,不能绑定到 int&
  • 若真要修改,别用 cbegin(),也别给 lambda 写 int& 参数,改用 int& 捕获或直接用普通迭代器

lambda 捕获方式影响 for_each 的副作用可见性

std::for_each 本身不保证 lambda 被调用几次(虽然实际是 N 次),但它不“返回”任何东西,所有状态变更必须靠捕获实现。很多人以为捕获 [&] 就万事大吉,结果发现变量没变——其实是 lambda 被复制了,而副本修改了局部副本。

典型表现:循环结束后计数器还是 0,或者容器没被修改。根本原因是 std::for_each 内部可能拷贝 lambda 对象(尤其在某些 libstdc++ 实现中)。

  • 安全做法:用 [&counter, &vec]() mutable { counter++; vec.push_back(...); } —— mutable 允许修改捕获的副本,但注意 vec 是引用,所以仍生效
  • 更稳方案:避免依赖 lambda 副作用,改用传统 for 循环,或把逻辑封装进函数对象(struct + operator()),显式控制拷贝语义
  • 别用 [=] 捕获需要修改的变量,除非你明确知道它会被拷贝且你希望修改副本

for_each 和 range-based for 性能差多少?

几乎没差别。现代编译器(GCC 9+、Clang 10+、MSVC 2019)对两者生成的汇编基本一致,都是简单指针/迭代器递增 + 解引用。所谓“for_each 更快”或“更慢”都是过时经验。

C++14
C++14

C++14 对 C++11 的修正与增强版本,适合旧系统维护和较老工具链兼容。

下载

真正影响性能的是 lambda 是否内联、是否触发别名分析失败、以及容器类型(vector 快,list 慢)。但这些和遍历语法无关。

  • 优先选 range-based for:写起来直觉,调试时断点位置清晰,IDE 支持好
  • 只在需要复用算法逻辑(比如和 std::transform 统一接口)、或配合其他 STL 算法组合使用时,才用 std::for_each
  • 别为了“函数式风格”硬套 for_each,C++ 不是 Haskell,可读性比范式更重要

std::for_each 在 std::map 遍历时容易漏掉 key/value 类型

std::map::iterator 解引用得到的是 std::pair,不是 std::pair。很多代码直接写 [](auto p) { p.first = ...; },结果编译失败:assignment of read-only member 'std::pair::first'。

这不是 bug,是 map 设计使然:key 必须不可变,否则破坏红黑树结构。但新手常忽略这个 const,尤其从 vector 切换过来时。

  • 正确访问 key:[](const auto& p) { std::cout —— p.first 是 const K&,只读安全
  • 修改 value:[](auto& p) { p.second = 42; } —— p.second 是 V&,可写
  • 别用 auto p(值拷贝),尤其是 value 类型大时;用 const auto& p 或 auto& p 明确意图

最常被忽略的点是:for_each 不检查迭代器有效性,也不做空范围保护。传入 v.end() 和 v.begin() 顺序颠倒、或容器在 lambda 中被意外清空,都会导致未定义行为——它不会像 range-for 那样天然规避这类问题。

C++免费学习笔记(深入):立即使用
在学习笔记中,你将探索 C++ 的入门与实战技巧!

相关文章

c++速学教程(入门到精通)
c++速学教程(入门到精通)

c++怎么学习?c++怎么入门?c++在哪学?c++怎么学才快?不用担心,这里为大家提供了c++速学教程(入门到精通),有需要的小伙伴保存下载就能学习啦!

下载

相关标签:

c++

本站声明:本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn

相关专题

更多
c语言const用法
c语言const用法

const是关键字,可以用于声明常量、函数参数中的const修饰符、const修饰函数返回值、const修饰指针。详细介绍:1、声明常量,const关键字可用于声明常量,常量的值在程序运行期间不可修改,常量可以是基本数据类型,如整数、浮点数、字符等,也可是自定义的数据类型;2、函数参数中的const修饰符,const关键字可用于函数的参数中,表示该参数在函数内部不可修改等等。

2023.09.20

2358

7

string转int
string转int

在编程中,我们经常会遇到需要将字符串(str)转换为整数(int)的情况。这可能是因为我们需要对字符串进行数值计算,或者需要将用户输入的字符串转换为整数进行处理。php中文网给大家带来了相关的教程以及文章,欢迎大家前来学习阅读。

2023.08.02

7039

3

int占多少字节
int占多少字节

int占4个字节,意味着一个int变量可以存储范围在-2,147,483,648到2,147,483,647之间的整数值,在某些情况下也可能是2个字节或8个字节,int是一种常用的数据类型,用于表示整数,需要根据具体情况选择合适的数据类型,以确保程序的正确性和性能。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

2024.08.29

3365

6

c++怎么把double转成int
c++怎么把double转成int

本专题整合了 c++ double相关教程,阅读专题下面的文章了解更多详细内容。

2025.08.29

4408

10

C++中int的含义
C++中int的含义

本专题整合了C++中int相关内容,阅读专题下面的文章了解更多详细内容。

2025.08.29

2985

10

lambda表达式
lambda表达式

Lambda表达式是一种匿名函数的简洁表示方式,它可以在需要函数作为参数的地方使用,并提供了一种更简洁、更灵活的编码方式,其语法为“lambda 参数列表: 表达式”,参数列表是函数的参数,可以包含一个或多个参数,用逗号分隔,表达式是函数的执行体,用于定义函数的具体操作。本专题为大家提供lambda表达式相关的文章、下载、课程内容,供大家免费下载体验。

2023.09.15

1091

5

python lambda函数
python lambda函数

本专题整合了python lambda函数用法详解,阅读专题下面的文章了解更多详细内容。

2025.11.08

345

7

Python lambda详解
Python lambda详解

本专题整合了Python lambda函数相关教程,阅读下面的文章了解更多详细内容。

2026.01.05

614

7

C++ Lambda 表达式与函数式编程
C++ Lambda 表达式与函数式编程

深入讲解 C++ Lambda 表达式与函数式编程范式,涵盖 Lambda 基础语法与返回值推导、值捕获与引用捕获的区别与陷阱、初始化捕获(C++14 广义捕获)、泛型 Lambda(auto 参数)、mutable 关键字修改捕获变量、std::function 类型擦除与函数包装、std::bind 参数绑定(及其被 Lambda 替代的趋势)、Lambda 在 STL 算法(sort/transform/for_each/remo

2026.05.06

789

22

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
C++ Core Guidelines
C++ Core Guidelines

共0课时 | 0人学习

C++ Reference
C++ Reference

共0课时 | 0人学习

C++ 官方标准说明
C++ 官方标准说明

共0课时 | 0人学习