书为第一版。scala为2.11.4,jdk1.7.45,操作系统Mac OS X Yosemite 10.10.1。
第十四章 模式匹配和样例类
14.1 JDK发行包有一个src.zip文件包含了JDK的大多数源代码。解压并搜索样例标签(用正则表达式case [^:]+:)。然后查找以//开头并包含[Ff]alls?thr的注释,捕获类似// Falls through或// just fall thru这样的注释。假定JDK的程序员们遵守Java编码习惯,在该写注释的地方写下了这些注释,有多少百分比的样例是会掉入到下一个分支的?
14.6 制作这样的树更好的做法是使用样例类。我们不妨从二叉树开始。 sealed abstract class BinaryTree case class Leaf(value : Int) extends BinaryTree case class Node(left : BinaryTree,right : BinaryTree) extends BinaryTree 编写一个函数计算所有叶子节点中的元素之和。
13.9 Harry Hacker写了一个从命令行接受一系列文件名的程序。对每个文件名,他都启动一个新的线程来读取文件内容并更新一个字母出现频率映射,声明为: val frequencies = new scala.collection.multable.HashMap[Char,Int] with scala.collection.mutable.SynchronizedMap[Char,Int] 当读到字母c时,他调用 frequencies(c) = frequencies.getOrElse(c,0) + 1 为什么这样做得不到正确答案?如果他用如下方式实现呢: import scala.collection.JavaConversions.asScalaConcurrentMap val frequencies:scala.collection.mutable.ConcurrentMap[Char,Int] = new java.util.concurrent.ConcurrentHashMap[Char,Int]
并发问题,并发修改集合不安全。
13.10 Harry Hacker把文件读取到字符串中,然后想对字符串的不同部分用并行集合来并发地更新字母出现频率映射。他用了如下代码: val frequencies = new scala.collection.mutable.HashMap[Char,Int] for(c <- str.par) frequencies(c) = frequencies.getOrElse(c,0) + 1 为什么说这个想法很糟糕?要真正地并行化这个计算,他应该怎么做呢?(提示:用aggregate) 并行修改共享变量,结果无法估计。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
import scala.collection.immutable.HashMap
val str = "abdcsdcd"
val frequencies = str.par.aggregate(HashMap[Char,Int]())(