Рассмотрим этот класс BigInt, который должен кэшировать некоторые общие значения в smallValues
:
object BigInt {
lazy val smallValues = Array(Zero, One, Two)
lazy val Zero = new BigInt(0, Array[Long]())
lazy val One = new BigInt(1, Array[Long](1))
lazy val Two = new BigInt(1, Array[Long](2))
private lazy val cacheSize = smallValues.length
def apply(num: Long): BigInt = {
// Is the number cached?
if (0 <= num && num < cacheSize) smallValues(num.toInt)
// Figure out the sign and make the number positive after that
else {
val (sign, value) = if (num < 0) (-1, num * -1) else (1, num)
new BigInt(sign, Array(value))
}
}
}
class BigInt private(val sign: Int, val num: Array[Long]) extends Ordered[BigInt] {
println("Constructing BigInt")
...
}
Проблема в том, что доступ к одному элементу массива заставляет вычислять все элементы:
scala> BigInt.smallValues(0)
Constructing BigInt
Constructing BigInt
Constructing BigInt
res0: BigInt = BigInt@2c176570
Как я могу это решить?
Edit: Глядя на предлагаемые решения, я действительно задаюсь вопросом, не будет ли более эффективным просто выделить их без дополнительных сложностей. Как вы думаете?