Rust 中的简单 for 循环

主要观点:

  • Rust 内置了很好的函数式编程工具,围绕迭代器概念,且注重性能和底层控制,使用函数式编程模式可兼具高性能和高可读性。
  • 对于不同的操作(如映射map、折叠fold、错误处理等),for循环和函数式编程方式各有优劣,需根据具体情况选择。

关键信息和重要细节:

  • 映射map

    • 简单for循环性能较好,通过Vec::with_capacity预先分配空间可避免部分内存重新分配从而更快约 30%。
    • map操作更具声明性,将原向量转为迭代器,map返回带有映射操作的迭代器,collect将迭代器转为向量,在 Rust 中map比简单for循环快约 6 倍,但具体原因未知,可能避免了分配或使用了 SIMD。
  • 折叠fold(减少)

    • 简单for循环在构建新集合时比reduce(Rust 中的fold)快很多,如对 50,000 项列表进行扁平化操作快约 180 倍。
    • 在迭代器级别使用fold可避免创建过多向量,但性能提升不明显,如使用chaincollect组合迭代器比concat快约 20%,仍比for循环慢约 4 倍,而使用flat_mapconcat快但仍比for循环慢 4 倍。
  • 错误处理和map

    • Rust 通过返回Result来处理错误,map在处理错误时功能等价于带有?操作符的for循环,with_capacity可自动获取大小提示。
    • 对于复杂的错误处理,for循环在某些情况下更方便,如在可失败的扁平化操作中,for循环比try_fold更易读和编写。
  • 结论

    • 进行集合转换时map很有用,但fold较复杂,在复杂场景中构建结构时fold有优势,for循环也有其优点,如可breakreturn,处理复杂错误更方便。
  • 更新

    • 发现一种通过修改fold的累加器来实现与简单for循环相同速度的方法,且在 Rust 中可安全修改移动的Vec,但仍认为for循环更易理解和处理错误。
    • 实验中使用简单i32整数,不同数据类型性能不同,如将i32转为f64map更快,转为String时性能差异消失,使用extend比手动在内部循环中推送稍快但仍比for循环慢。

总结:Rust 中函数式编程和for循环各有优势,应根据具体情况选择,同时要考虑数据类型等因素对性能的影响。

阅读 7
0 条评论