news 2026/4/28 16:17:29

std::ranges、std::views和懒加载

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
std::ranges、std::views和懒加载

1、std::string::npos是C++中std::string类定义的一个静态常量,通常用于表示“未找到”或“直到字符串结束”。

常见用途:

表示查找操作,但未找到结果

std::string str = "hello word"; size_t pos = str.find("xyz"); if(pos == std::string::npos) { //查到结尾,但未找到 }

表示从某个位置开始,截取到字符串末尾

std::string str = "hello world"; std::string sub = str.substr(6,std::string::npos); //表示从位置6开始,截取到字符串末尾

2、惰性视图:是一种优化程序性能的编程技术。它的核心理念是:把要做的工作记录下来,但不立即执行,等到需要结果的那一刻,才进行真正的计算。

3、C++20引入的Ranges库是标准库模板STL的一次重大升级,它通过“视图”和“管道符 |”提供了一种更现代、更强大、也更安全的数据处理方式。

核心概念,Ranges库建立在几个相互关联的核心概念之上:

(1)范围:一个可以遍历的元素序列的抽象。如标准容器库vector,list,array等都是范围

(2)视图:一个轻量级的、非持有的范围,它不会复制数据,而是对底层数据进行某种操作(如筛选、转换等)并提供一个“视图”。视图的计算是惰性的,即只有在需要时才计算,这为性能优化提供了巨大空间。

(3)范围适配器:返回视图的函数或对象。它们是构建数据处理管道的基本单元,通过管道符 | 进行组合,数据从左向右流动,逻辑清晰直观。

(4)管道符:用于组合视图的操作符。R | A | B的写法让数据处理像流水线一样易于理解。

Ranges库并非仅仅是语法糖,它代表了一种全新的、更函数式的C++编程范式。

#include <string> #include <vector> #include <algorithm> #include <ranges> #include <iostream> int main() { std::string word = "apple"; auto hasWord = [&word](const std::string& s) {return s.find(word) != std::string::npos;}; std::vector<std::string> words = { "apple pie", "banana split", "apple tart", "cherry cobbler" }; auto res = words | std::views::filter(hasWord); for (auto s : res) { std::cout << s << std::endl; } std::vector<int> input{0,1,2,3,4,5,6,7,8,9,10}; std::vector<int> intermediate, output; std::copy_if(input.begin(), input.end(), std::back_inserter(intermediate), [](int i) {return i % 3 == 0; }); std::transform(input.begin(), input.end(), std::back_inserter(output), [](const int i) {return i * i; }); for (auto i : intermediate) { std::cout << i << " "; } std::cout << std::endl; for (auto i : output) { std::cout << i << " "; } std::cout << std::endl; auto output2 = input | std::views::filter([](const int i) {return i % 3 == 0; }); auto output3 = input | std::views::transform([](const int i) {return i * i; }); for (auto i : output2) { std::cout << i << " "; } std::cout << std::endl; for (auto i : output3) { std::cout << i << " "; } std::cout << std::endl; auto output4 = input | std::views::filter([](const int i) {return i % 3 == 0; }) | std::views::transform([](const int i) {return i * i; }); std::cout << "------------------" << std::endl; for (auto i : output4) { std::cout << i << " "; } std::cout << std::endl; return 0; }

4、管道的作用

左边:数据源(容器、范围)

右边:视图适配器

效果:将数据源“喂给”视图适配器处理

5、懒加载的具体体现

#include <iostream> #include <vector> #include <string> #include <ranges> int main() { std::vector<std::string> words = { "apple pie", "banana split", "apple tart" }; int filterCalls = 0; auto hasApple = [&filterCalls](const std::string& s) { filterCalls++; std::cout << "Filter checking: " << s << std::endl; return s.find("apple") != std::string::npos; }; // 创建视图 - 不会触发任何过滤检查 auto view = words | std::views::filter(hasApple); std::cout << "After view creation, filter calls: " << filterCalls << std::endl; // 第一次遍历 - 触发过滤 std::cout << "\nFirst iteration:\n"; for (const auto& s : view) { std::cout << " Result: " << s << std::endl; } std::cout << "Filter calls after first iteration: " << filterCalls << std::endl; // 第二次遍历 - 再次触发过滤 std::cout << "\nSecond iteration:\n"; for (const auto& s : view) { std::cout << " Result: " << s << std::endl; } std::cout << "Filter calls after second iteration: " << filterCalls << std::endl; }

与普通容器相比:

#include <iostream> #include <vector> #include <string> #include <ranges> int main() { std::vector<std::string> words = {"apple pie", "banana split", "apple tart"}; // 方式1:立即求值的传统方式 auto hasApple = [](const std::string& s) { return s.find("apple") != std::string::npos; }; std::vector<std::string> eager_result; std::copy_if(words.begin(), words.end(), std::back_inserter(eager_result), hasApple); // eager_result 现在就包含了所有匹配的字符串(副本) // 方式2:惰性求值的视图方式 auto lazy_view = words | std::views::filter(hasApple); // lazy_view 不包含数据,只是知道如何过滤 // 主要区别: // 1. 内存:eager_result 占用额外内存,lazy_view 不占用 // 2. 时间:eager_result 立即计算,lazy_view 延迟计算 // 3. 原数据修改:lazy_view 会反映原数据的变化 }

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/4/28 16:13:24

新概念英语第二册44_Through the forest

Lesson 44: Through the forest 穿过森林Key words and expressions Anne Sterling 安斯特林risk 危险&#xff0c;冒险picnic 野餐edge 边缘strap 带&#xff0c;皮带possession 所有be…

作者头像 李华
网站建设 2026/4/28 16:10:23

2026工程基建与零基础跑通篇:YOLO26的EMA(指数移动平均)权重更新机制源码精读与应用

导语:为什么EMA是YOLO26中最被低估的“质量开关”? 很多工程师把注意力放在YOLO26的无NMS、端到端这些光鲜亮丽的新特性上,但真正决定你部署到生产环境后模型“稳不稳”的,其实是那个默认开启、不起眼的ema_decay参数。根据Ultralytics官方2026年1月14日发布的YOLO26正式公…

作者头像 李华
网站建设 2026/4/28 16:08:22

终极指南:AppleRa1n iOS激活锁离线绕过解决方案深度解析

终极指南&#xff1a;AppleRa1n iOS激活锁离线绕过解决方案深度解析 【免费下载链接】applera1n icloud bypass for ios 15-16 项目地址: https://gitcode.com/gh_mirrors/ap/applera1n AppleRa1n是一款基于Palera1n越狱工具修改的iOS激活锁绕过工具&#xff0c;专门为i…

作者头像 李华
网站建设 2026/4/28 16:04:24

2026届毕业生推荐的五大降AI率工具实测分析

Ai论文网站排名&#xff08;开题报告、文献综述、降aigc率、降重综合对比&#xff09; TOP1. 千笔AI TOP2. aipasspaper TOP3. 清北论文 TOP4. 豆包 TOP5. kimi TOP6. deepseek 能借助智能算法帮用户把文本重复率给降下来的在线工具&#xff0c;被称作降重网站&#xff0…

作者头像 李华
网站建设 2026/4/28 16:03:23

CompressO视频压缩工具:如何让大文件变小而不损失画质

CompressO视频压缩工具&#xff1a;如何让大文件变小而不损失画质 【免费下载链接】compressO Convert any video/image into a tiny size. 100% free & open-source. Available for Mac, Windows & Linux. 项目地址: https://gitcode.com/gh_mirrors/co/compressO …

作者头像 李华