如何解决将理解力转换为LazyList
我有
- 文件列表(
filepaths
) - 一种读入并处理文件(
loadData
)的方法 - 一种用于计算该文件统计信息的方法
仅当我们还需要计算统计信息时,我才想读取文件。下面的行将遍历文件路径,并返回其名称和文件内容。
for((name,path) <- filepaths) yield (name,loadData(path))
是否可以对LazyList
进行这样的理解,以便对loadData
部分进行懒惰的评估?
解决方法
for comprehension
只是flatMap
和map
函数组合的语法糖。您可以使用地图功能来做到这一点:
def loadData(path: String): String = {
println(s"launch loadData on $path")
s"${path}_suffix"
}
val filePaths = Seq("p1" -> "path1","p2" -> "path2")
val lazyList = filePaths.to(LazyList).map{
case (name,path) => name -> loadData(path)
}
println(lazyList)
println(lazyList.force)
// output will be:
//LazyList(<not computed>)
//launch loadData on path1
//launch loadData on path2
//LazyList((p1,path1_suffix),(p2,path2_suffix))
在这里我们看到loadData
仅在需要下一个元素时才求值。
绝对有可能。
for ((name,path) <- filepaths) yield (name,loadData(path))
只是语法糖
filepaths.map { x =>
val (name,path) = x
(name,loadData(path)
}
(这可能不是编译器实际要解决的(我忘记了是否会有多个函数(一个提取对,一个调用loadData
))
由于map
上有一个LazyList
,因此如果filepaths
是LazyList
,它将起作用。
也就是说,这并不是最大程度的懒惰:获取第n
个条目需要评估第(n - 1)
个条目。
当然,只要您有Seq[(A,B)]
(或Iterable[(A,B)]
/ Traversable[(A,B)]
),就值得考虑您真正想要的是Function1[A,B]
还是{{1 }}(可以认为是构建Map[A,B]
的子集的简单方法)。
Function[A,B]
(请注意,// assuming that filepaths is an `Iterable[(A,B)]`
filepaths.toMap.mapValues(loadData(_))
可以省略)。
这将是非严格的(在您查找给定的(_)
之前不会调用loadData
),但是它不会是最大程度的懒惰(没有任何备注:每次查找都会导致name
通话)。如果您想要最大程度的懒惰,则必须实现自己的备忘录。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。