Understanding Spread and Rest Operator

Understanding Spread and Rest Operator

Got confused between when to use spread and rest operator, look no more😎

·

3 min read

Spread Operator

So ever gone through the hassle of passing n number of arguments to a function and handling it there, uhh🤯. So much trouble.

const add = (a,b,c,d,e) => a + b + c + d + e

console.log(add(1,2,3,4,5)) // Output: 15

This might get confusing when you are working in a bigger project and it's quite tedious to debug and keep track of each variable.

So we have Spread {...} Operator to the rescue. 😋

const add = (a,b,c,d,e) => a + b + c + d + e
const arr = [1,2,3,4,5] // First we store all the parameters in an array
console.log(add(...arr)) // arr is expanded/spread to 1,2,3,4,5
// Output: 15

In the above example a, b, c, d, e gets assigned with 1, 2, 3, 4, 5 respectively. And if the arguments passed to add() were less than it's expected arguments i.e. if we only pass 1, 2, 3, 4 then it will map to a, b, c, d and e will remain undefined, and so on.

As we can see Spread Operator spreads / expands the content of the iterables.

Note: Spread Operator can only work with Iterable entites.

Which means we can also spread strings, objects.

*const str = "Hello"
console.log([...str]) // Output: ['H', 'e', 'l', 'l', 'o']

We can also concatenate two arrays or objects i.e we can merge two arrays or objects and also add extra content if required.

// Array
let arr1 = [1, 2, 3]
let arr2 = [4, 5, 6]
console.log([...arr1, ...arr2]) // Output: [1,2,3,4,5,6]

// Object
let obj1 = { foo: 'bar', x: 50 }
let obj2 = { foo: 'rab', y: 25 }
console.log({ ...obj1, ...obj2 }) // Output: Object {foo: 'rab', x: 50, y: 25}

Cloning Arrays and Objects

const arr1 = [1, 2, 3]
const arr2 = [...arr1]  // creates a deep copy => [1, 2, 3]

const obj1 = { foo: 'bar', x: 50 }
const obj2 = {...obj1}  // creates a deep copy => { foo: 'bar', x: 50 }

Note: Spread Operator goes one level deep when copying an array. So, it may be not correct match for copying multidimensional arrays

Rest Operator

Rest operator is exactly opposite of spread operator i.e. spread operator expands whereas rest operator collects elements and shrinks/condenses them into a single element.

Suppose we need to create a function which takes multiple number of inputs and we need to return their addition and the number of input arguments is dynamic i.e. we can't predict how many will be there.

  • One way is to make variables as many as the number of inputs. This may work but it's a bad approach
  • On the other hand we can use rest operator to make our life easy.
const getSum = (...args) => {
      let sum = 0
        for(let arg of args)  
             sum += arg
       return sum
}

alert(getSum(1, 3)) // Output: 4
alert(getSum(1, 2, 3, 4))  // Output: 10
alert(getSum(5)) // Output: 5

We can also choose which parameters we want separately and gather only the rest parameters.

const numbers = (num1, num2, ...num) => {
         alert(num1 + num2)  // Output: 15
         // num= [8, 6, 9]
         alert(num[0])   // Output: 8
         alert(num.length)   // Output: 3
}

numbers(5, 10, 8, 6, 9)

Note: The rest parameters must always be at the end
const func = (arg1, ...args, argN) => { // error}
The ...rest must always be last

Conclusion

{...spread} and {...rest} are the opposite sides of same coin. When we need iterable to expand it's content we use spread and when we want to collect and condense multiple data elements into a single element we use rest.

Â