0

This next example function works just fine:

const data = [1, 2, 3, 4, 5];

function insertAndShift(arr, number) {
  const cutOut = arr.splice(-number);
  return [...cutOut, ...arr];
}

console.log('Output: ', insertAndShift(data, 2));
// Output: [4,5,1,2,3]

However, when I call the function another time, I suddenly get a wrong response:

const data = [1, 2, 3, 4, 5];

function insertAndShift(arr, number) {

  // The next starting array should be [1,2,3,4,5] on both occasions.
  // However, on the second occasion it will only be [1,2,3].
  // Which was the array in the first time the function was called.
  console.log('arr: ', arr);

  const cutOut = arr.splice(-number);
  return [...cutOut, ...arr];
}

console.log('Output: ', insertAndShift(data, 2));
// Output: [4,5,1,2,3]

console.log('Output: ', insertAndShift(data, 3));
// Output: [1,2,3]
// Should be: [3,4,5,1,2]

Is this a scoping issue? Or what is exactly happening here?

1
  • 2
    splice mutates the array. So after your first call data has changed. Commented Nov 20, 2019 at 13:13

2 Answers 2

3

In Javascript, all, non primitive, variable are passed "by reference", which mean you can modify a variable from inside a function. This is where you need to be careful. Usually, you would clone your array before doing anything with it, this way, the original array won't be affected by your mutations.

const data = [1, 2, 3, 4, 5];

function insertAndShift(arr, number) {
  let clonedArray = [...arr];
  // The next starting array should be [1,2,3,4,5] on both occasions.
  // However, on the second occasion it will only be [1,2,3].
  // Which was the array in the first time the function was called.

  const cutOut = clonedArray.splice(-number);
  return [...cutOut, ...clonedArray];
}

console.log('Output: ', insertAndShift(data, 2));

console.log('Output: ', insertAndShift(data, 3));

Sign up to request clarification or add additional context in comments.

6 Comments

Nice! Ty. Would you happen to have an article/blogpost regarding this specific topic? Or a keyword I should search for?
not all variables are passed by reference ... eg primitive values.
@NinaScholz you are right, i've edited my answer for accuracy.
Is there a reason you're using let instead of const for the clonedArray?
@Remi you can check out this article I have not red it in it's entirity but it's seams pretty accurate.
|
2

Beside of cloning an array, you could take parts directly with Array#slice and build a new array - without using mutating Array#splice.

function insertAndShift(array, number) {
    return [...array.slice(-number), ...array.slice(0, -number)];
}

const data = [1, 2, 3, 4, 5];

console.log(...insertAndShift(data, 2)); // [4, 5, 1, 2, 3]
console.log(...insertAndShift(data, 3)); // [3, 4, 5, 1, 2]

1 Comment

Very nice. I will accept the answer of Nicolas since that answers my question on the 'change of the variable'. But upvoted yours since this is a nice addition to the function.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.