Как вы думаете, что выдает?Scala recursive val поведение
val foo: String = "foo" + foo
println(foo)
val foo2: Int = 3 + foo2
println(foo2)
Ответ:
foonull
3
Почему? Есть ли какая-то деталь в спецификации, которая описывает/объясняет это?
EDIT: Для того, чтобы прояснить мое удивление, - я понимаю, что foo
не определено в val foo: String = "foo" + foo
, и именно поэтому он имеет значение по умолчанию null
(ноль для целых чисел). Но это не кажется очень «чистым», и я вижу здесь мнения, которые согласны со мной. Я надеялся, что компилятор помешает мне сделать что-то подобное. Это имеет смысл в некоторых частных случаях, например, при определении Stream
s, которые являются ленивыми по своей природе, но для строк и целых чисел я ожидал бы либо прекратить меня из-за переназначения в val, либо сказать мне, что я пытаюсь использовать неопределенное значение , точно так же, как если бы я написал val foo = whatever
(учитывая, что whatever
так и не определился).
Чтобы еще больше усложнить ситуацию, @ dk14 указывает, что это поведение присутствует только для значений, представленных как поля, и не происходит в блоках, например.
val bar: String = {
val foo: String = "foo" + foo // error: forward reference extends...
"bar"
}
Какое поведение вы ожидаете? –
Компилятор говорит мне «переназначение в val» или что-то в этом роде. Или сказать мне, что он не знает, что такое 'foo' (поскольку лексический анализ компилятора еще не сохранил этот токен, поскольку он еще не был полностью определен). Определенно не давая ему временное значение «null», которое больше похоже на JavaScript, чем на Scala (с неопределенным, а не нулевым). – slouc
@slouc также замечает разницу в поведении при замене 'val' 'def'. – fxlae