我的代码:
val byDate = data.groupBy(_._1).map(t => t._1 -> t._2.map(_._2).toMap).flatMap {
...
}
var incomplete: Option[LocalDate] = None
val filtered = (incomplete.map { i =>
println(s"i = $i")
byDate.filterKeys { d =>
println(s"dd = $d vs i = $i")
}
}).getOrElse(byDate)
如何理解(incomplete.map {})
的作用?从输出,我猜它开始另一个线程?我对吗?因为,上述代码的输出被其他输出分开(在上述程序之后由某些代码打印出来)。
... other outputs generated by some codes after the above piece of codes ...
dd = 2018-05-11 vs i = 2018-05-12
dd = 2018-05-10 vs i = 2018-05-12
dd = 2018-05-13 vs i = 2018-05-12
dd = 2018-05-14 vs i = 2018-05-12
... other outputs generated by some codes after the above piece of codes ...
dd = 2018-05-10 vs i = 2018-05-12
dd = 2018-05-11 vs i = 2018-05-12
更新
我已经有一个原因:filterKeys does evaluation lazily
,因此,只有在filtered
使用后,它才会开始评估。
答案 0 :(得分:1)
Scala集合上调用的操作(如map)是顺序执行还是并行执行,取决于集合的类型。
默认情况下导入的集合是顺序的,但只需在集合上调用par
即可实现并行执行。
让我们举一个例子:
(1 to 10).map { i => println(s"accessing sequentially $i") }
这会按预期提供以下顺序输出:
accessing sequentially 1
accessing sequentially 2
accessing sequentially 3
accessing sequentially 4
accessing sequentially 5
accessing sequentially 6
accessing sequentially 7
accessing sequentially 8
accessing sequentially 9
accessing sequentially 10
然而,我们可以使用par
方法
(1 to 10).par.map { i => println(s"accessing parallel $i") }
其中给出了以下输出:
accessing parallel 1
accessing parallel 2
accessing parallel 3
accessing parallel 4
accessing parallel 5
accessing parallel 8
accessing parallel 9
accessing parallel 10
accessing parallel 6
accessing parallel 7
我认为您看到混合输出语句的原因可能是,您的程序包含其他一些线程?
另一种可能性是,您的收藏品是并行类型。
您可以安全地删除您看到的parantheses,而无需更改程序的输出。
答案 1 :(得分:1)
括号可以在scala中启动一个新线程吗?
没有
如何理解
(incomplete.map {})
的作用?
与没有括号的incomplete.map {...}
完全相同。括号完全是多余的。也许编写该代码的人认为括号需要在getOrElse
之后调用map
,但事实并非如此。 incomplete.map {...}.getOrElse(byDate)
仍然是有效的语法,完全等效。
因为,上述代码的输出被其他输出分开(在上述程序之后由某些代码打印出来)。
无法确定为什么在没有看到其余代码(或至少是byDate
的类型)的情况下发生这种情况是不可能的,但有一个合理的理论是byDate
是比方说,一个流,其元素在迭代时进行评估。因此,如果byDate
的定义包含print语句,则会在迭代byDate
时执行这些语句。
另一个理论是你只是在其他地方启动多个线程。