I did some micro-benchmarks with foreach and while and to my surprise loop actually lost, though there is less difference with latest version of Scala. Here are the results (Azul JDK 11.0.12 running on M1)
Scala 2.13.6
Benchmark Mode Cnt Score Error Units
HashMapBenchmark.vectorMutable thrpt 10 53220.300 ± 220.481 ops/s
HashMapBenchmark.whileMutable thrpt 10 49586.007 ± 48.883 ops/s
Scala 2.12.15
Benchmark Mode Cnt Score Error Units
HashMapBenchmark.vectorMutable thrpt 10 41298.593 ± 245.915 ops/s
HashMapBenchmark.whileMutable thrpt 10 36607.998 ± 476.617 ops/s
Benchmark code
case class Cookie(name: String, value: String)
state.cookies = (1 to 1000).map(i => Cookie(s"name_$i", s"value_$i")).toVector
@Benchmark
def vectorMutable(state: BenchmarkState, blackhole: Blackhole): Unit = {
val map = new mutable.HashMap[String, String]()
state.cookies.foreach(c => map.put(c.name, c.value))
blackhole.consume(map)
}
@Benchmark
def whileMutable(state: BenchmarkState, blackhole: Blackhole): Unit = {
val map = new mutable.HashMap[String, String]()
var i = 0
while (i < state.cookies.length) {
val cookie = state.cookies(i)
map.put(cookie.name, cookie.value)
i+=1
}
blackhole.consume(map)
}
How is it even possible?