Вот пример фрагмента кода, который на первый взгляд выглядит так, будто scalac
мог бы легко его оптимизировать:
val t0 = System.nanoTime()
for (i <- 0 to 1000000000) {}
val t1 = System.nanoTime()
var i = 0
while (i < 1000000000) i += 1
val t2 = System.nanoTime()
println((t1 - t0).toDouble / (t2 - t1).toDouble)
Приведенный выше код печатает 76.30068413477652
, и соотношение, похоже, ухудшается по мере увеличения количества итераций.
Есть ли какая-то особая причина, по которой scalac
предпочитает не оптимизировать for (i <- L to/until H)
в любую форму байт-кода, которую javac
генерирует для for (int i = L; i < H; i += 1)
? Может быть, это потому, что Scala предпочитает делать вещи простыми и ожидает, что разработчик просто прибегнет к более производительным формам, таким как цикл while
, когда требуется чистая скорость цикла? Если да, то почему это хорошо, учитывая частоту таких простых циклов for?
foreach
выглядит для объекта, который вы передаете. Есть много вещей, которые могут пойти не так с такой оптимизацией. - person drexin   schedule 23.09.2013<Int> to/until <Int>
— разве такая информация не доступна статически во время компиляции с достаточной надежностью? - person Erik Kaplun   schedule 23.09.2013cfor
иcforRange
, которые обеспечивают именно такую оптимизацию с помощью макросов. - person Travis Brown   schedule 23.09.2013cfor
могли просто оптимизировать существующие конструкцииfor (...)
, что, я уверен, могут сделать макросы Lisp. - person Erik Kaplun   schedule 23.09.2013foreach
. после встраивания вы получите циклwhile
. Эта оптимизация работает не только для диапазонов. Scalac не должен знать о классеRange
- это не часть самого языка. Как уже отмечалось, в крайне редких случаях, когда вам действительно нужны такие оптимизации во время компиляции, вы можете использовать сторонние библиотеки, такие какScalaxy
. - person senia   schedule 23.09.2013