Scala中高效且可组合的foreach替代方案
Scala中高效执行副作用并返回原列表的方案
要实现遍历大列表执行副作用操作,同时返回原列表进行后续链式调用,且避免复制列表的需求,有两种简洁高效的方案:
方案一:使用Scala 2.13+标准库的also方法
Scala 2.13及以上版本提供了also扩展方法(需导入scala.util.chaining._),它会对调用对象执行指定操作,然后返回原对象,完美契合需求:
import scala.util.chaining._ lst .many_operations() .also(_.foreach(x => f(x))) // 执行副作用,不复制列表 .something_else() // 继续调用原列表的方法
also的核心逻辑是接收一个函数,将当前集合传入函数执行foreach(副作用操作),随后直接返回原集合,全程不会创建新列表,内存开销和单独调用foreach完全一致。
方案二:自定义扩展方法(兼容旧版Scala)
如果使用Scala 2.13以下版本,可以通过隐式类给集合扩展一个tapEach方法,实现相同效果:
// 定义隐式类,扩展所有Iterable类型 implicit class IterableTapOps[A](private val iterable: Iterable[A]) extends AnyVal { def tapEach(f: A => Unit): Iterable[A] = { iterable.foreach(f) // 遍历执行副作用 iterable // 返回原集合 } } // 使用方式 lst .many_operations() .tapEach(x => f(x)) .something_else()
这个自定义方法同样不会复制列表,仅遍历原集合执行操作后返回自身,内存效率拉满。
为什么不用map?
你提到的map方案会构造新列表,对极大列表来说意味着要复制所有元素,带来巨大的内存开销;而上述两种方案都只是遍历原集合,没有复制操作,在性能和内存占用上更优。
内容的提问来源于stack exchange,提问作者Caleb
相关产品推荐
相关产品推荐

