Reputation: 7419
In Scala, the val
keyword declares an immutable variable. So if you declare val x = 3
, it stays 3. But if you use var
, it can change.
But what happens if you declare an instance of a class with val
? For example, take this class Point
class Point(_x: Int, _y: Int) {
var x = _x
var y = _y
def doubleValues = {
x *= 2
y *= 2
}
}
First, I declare var location = new Point(2,2)
Then run
println(location.x)
println(location.y)
location.doubleValues
println(location.x)
println(location.y)
The output, as expected, is
2
2
4
4
But if I rerun and use the val
keyword to declare location, the result is the same. So even though location
was declared immutable, the mutable variables inside it are still mutable.
So then what does actually happen when you declare an instance of a class with val
? What exactly is the difference between using var
and val
?
Upvotes: 1
Views: 114
Reputation: 17431
With a var
you can change which Point
it is; with a val
you can't:
var x = new Point(2, 2)
x = new Point(3, 2)
val y = new Point(2, 2)
y = new Point(3, 2) // won't compile
Conversely if I make an object containing a val
, I can't change that value "inside" the object, even though I can change the object itself:
class Q(i: Int) {val x: Int = i}
var q = new Q(4)
q = new Q(6)
q.x = 2 // won't compile
To make an object truly immutable you need to use val
"all the way down". A common pattern is to have all your "inner" objects immutable, and then have some "top-level" object which is mutable, either explicitly (with var
) or by using something like the State
monad. There's relatively little value in having an "immutable" object with mutable members.
Upvotes: 3