Difference between immutable references and immutable values in Scala
This post explores the similarities and differences between immutable values and immutable references. The state of immutable values cannot be changed. Immutable references are variables that cannot be reassigned.
Scala supports immutable and mutable coding styles, so the Scala programmer is responsible for knowing the two different styles and following the design philosophy of the codebase.
Mutable references
Let’s use the var
keyword to assign the variable x
to an integer value.
var x: Int = 6
x
can be reassigned to other integers, so it’s a mutable reference.
x = 10 // this works!
Scala is strongly typed, so once a variable is typed as an integer, it cannot be assigned to values of other types.
x = "bob" // error: type mismatch
Immutable references
Let’s use the val
keyword to assign the variable location
to a string value via an immutable reference.
val location: String = "airplane"
location
cannot be reassigned to another string value because it’s an immutable reference.
location = "school" // error: reassignment to val
Comparing Scala variables with variables in a weakly typed language
Variables in weakly typed programming languages like JavaScript are mutable and can be assigned to values of any type. This is perfectly valid JavaScript code.
var y = “dog”
y = 55
y = {}
A Scala variable with the Any
type behaves like a JavaScript variable because it is an immutable reference that can point to values of different types.
var person: Any = “craig”
person = 22
person = List()
Immutable values
Let’s write a Person
class that creates immutable objects.
class Person(val firstName: String, val lastName: String) {
def fullName(): String = {
s”$firstName lastName”
}
}
Let’s instantiate the Person
class to create an immutable object:
val bob = new Person("bob", "loblaw")
The bob
variable is an immutable reference to an immutable object. There is no way for us to change the state of the object once it is instantiated and that’s why it’s immutable.
Mutable values
Let’s create a Dog
class that creates mutable objects.
class Dog(var breed: String) {
def about(): String = {
s”I am a $breed dog”
}
}
Let’s create an instance of the Dog
class.
val fido = new Dog(“lab”)
The fido
variable is an immutable reference to a mutable object. fido
can’t be reassigned, but the instance can be mutated.
fido.breed // “lab”
fido.breed = “pug”
fido.breed // “pug”
Scala gives a lot of decision making power to the programmer
Some programming langauges only allow for immutable references (e.g. Haskell) and other languages only allow for mutable references (e.g. Ruby). Scala let’s programmers choose if they want to use immutable references or mutable references.
The Scala design philosophy of giving decision making power to the programmer extends to the highest level of the language. Scala can be used as an object oriented language or a purely functional language.