7

The Road to Immutability in JavaScript

 1 year ago
source link: https://devm.io/javascript/javasccript-immutability-type-system
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
neoserver,ios ssh client

Hitchhiking through the JavaScript jungle

The Road to Immutability in JavaScript


Immutability in JavaScript is increasingly being talked and written about. Of course, we’re all convinced that this immutability is a very good idea—but why actually? And how is it done? What do I have to pay attention to?

Before we dive into the actual topic, let's take a look at the theory behind it. This is mainly about JavaScript’s type system and how the engine handles different types. And yes, JavaScript has a type system, albeit a weak one. In JavaScript, there are two different types: primitive and composite. Primitive types are for example strings, numbers, or booleans. Composite types are arrays and objects. The main difference between the two is that they assign primitive types by-value and composite types by-reference. The best way to see the effect that the assignments have is by looking at a concrete example in Listing 1.

Listing 1: Changing data structures

let str = 'Hello World!';
let obj = {
  name: 'Klaus',
};
 
function mutate(s, o) {
  s = 'Good morning';
  obj.name = 'Peter';
 
  console.log(s);
  console.log(obj);
}
 
mutate(str, obj);
 
console.log(str);
console.log(obj);

The code first defines two variables: a string and an object. The _mutat_e function has two parameters: a string and an object. The function modifies both arguments. It replaces the string, which is passed by-value, with the value Good morning and for the object, it changes the name property to the value Peter. For verification, we print both values on the console. Finally, in the example, we call the function and write both values to the console. You can see the script’s output—whether you run it in the browser or via Node.js—in Listing 2.

Listing 2: Sample output

Good morning
{ name: 'Peter' }
Hello World!
{ name: 'Peter' }

The first output is the string Good morning, so the first argument has a new value, just like the name property of the passed object. The output outside the function looks a little different: The primitive variable remains unchanged at the original value and the object has taken the modification from the function. The reason is that when you call the function, for the primitive value you pass a copy of the value to the function. For the composite type, you simply pass a reference to the memory area of the object. This means that a change in the function modifies the original object. Theoretically, you could take advantage of this JavaScript peculiarity and do without return values of functions. The problem here is that a function changes its environment without it being directly apparent from its signature. Therefore, manipulation is a side effect of the function. These side effects can still be okay in individual cases but if an application grows or the functionality is outsourced to a separate library, side effects are no longer appropriate. They bring with them a large potential for errors.

Now, we can ask ourselves: Can't something be done about the mutability of objects?

Protect objects against changes by freezing them

The short and simple answer is: Yes, it’s possible to protect an object from change. For such cases, the JavaScript standard provides the Object.freeze method. You pass the object you want to protect to it and afterwards, no more changes are possible. In our example, this means that you have to insert the line Object.freeze(obj) as seen in Listing 3.

Listing 3: Protect objects from changes

let obj = { name: 'Klaus' };
Object.freeze(obj);
 
function mutate(o) {
  o.name = 'Peter';
  console.log(o);
}
 
mutate(obj);
console.log(obj);

The result of this change takes some getting used to. The attempt to manipulate the object is simply ignored; the JavaScript engine doesn’t give any feedback in the form of an exception. You ...


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK