1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
|
// Tests to show that various `collect` functions avoid calling
// both `PartialFunction#isDefinedAt` and `PartialFunction#apply`.
//
object Test {
def f(i: Int) = { println("f(" + i + ")"); true }
class Counter {
var count = 0
def apply(i: Int) = synchronized {count += 1; true}
}
def testing(label: String)(body: => Any) {
println(s"\n=$label=")
println(body)
}
def main(args: Array[String]) {
testing("List.collect")(List(1, 2) collect { case x if f(x) && x < 2 => x})
testing("List.collectFirst")(List(1, 2) collectFirst { case x if f(x) && x < 2 => x})
testing("Option.collect")(Some(1) collect { case x if f(x) && x < 2 => x})
testing("Option.collect")(Some(2) collect { case x if f(x) && x < 2 => x})
testing("Stream.collect")((Stream(1, 2).collect { case x if f(x) && x < 2 => x}).toList)
testing("Stream.collectFirst")(Stream.continually(1) collectFirst { case x if f(x) && x < 2 => x})
import collection.parallel.ParIterable
import collection.parallel.immutable.ParVector
import collection.parallel.mutable.ParArray
testing("ParVector.collect") {
val counter = new Counter()
(ParVector(1, 2) collect { case x if counter(x) && x < 2 => x}, counter.synchronized(counter.count))
}
testing("ParArray.collect") {
val counter = new Counter()
(ParArray(1, 2) collect { case x if counter(x) && x < 2 => x}, counter.synchronized(counter.count))
}
object PendingTests {
testing("Iterator.collect")((Iterator(1, 2) collect { case x if f(x) && x < 2 => x}).toList)
testing("List.view.collect")((List(1, 2).view collect { case x if f(x) && x < 2 => x}).force)
// This would do the trick in Future.collect, but I haven't added this yet as there is a tradeoff
// with extra allocations to consider.
//
// pf.lift(v) match {
// case Some(x) => p success x
// case None => fail(v)
// }
testing("Future.collect") {
import concurrent.ExecutionContext.Implicits.global
import concurrent.Await
import concurrent.duration.Duration
val result = concurrent.future(1) collect { case x if f(x) => x}
Await.result(result, Duration.Inf)
}
// TODO Future.{onSuccess, onFailure, recoverWith, andThen}
}
}
}
|