Inną kwestią jest to, że pierwsze zdanie jest analizowane jako:
scala> List(1,2,3).++(List(4,5))
res0: List[Int] = List(1, 2, 3, 4, 5)
Natomiast drugi przykład jest analizowany jako:
scala> List(4,5).:::(List(1,2,3))
res1: List[Int] = List(1, 2, 3, 4, 5)
Więc jeśli używasz makr, powinieneś się zachować ostrożność.
Poza tym, ++
dla dwóch list wywołuje się, :::
ale z większym obciążeniem, ponieważ prosi o wartość domyślną, aby mieć konstruktora z listy do listy. Ale mikrobenchmarki nie okazały niczego przydatnego w tym sensie, myślę, że kompilator optymalizuje takie wywołania.
Mikro-Benchmarki po rozgrzaniu.
scala>def time(a: => Unit): Long = { val t = System.currentTimeMillis; a; System.currentTimeMillis - t}
scala>def average(a: () => Long) = (for(i<-1 to 100) yield a()).sum/100
scala>average (() => time { (List[Int]() /: (1 to 1000)) { case (l, e) => l ++ List(e) } })
res1: Long = 46
scala>average (() => time { (List[Int]() /: (1 to 1000)) { case (l, e) => l ::: List(e ) } })
res2: Long = 46
Jak powiedział Daniel C. Sobrai, możesz dołączyć zawartość dowolnej kolekcji do listy za pomocą ++
, podczas gdy za pomocą :::
możesz łączyć tylko listy.
:::
jest operatorem prefiks jak wszystkich metod zaczynając: