Move zeroes to end of array in javascript - how to return nothing?

I am attempting to complete a leetcode.com question in JS. I am new to algorithms in general, and am having some trouble getting my first submission accepted.

The question specifies the following:

Given an array nums, write a function to move all 0's to the end of it while maintaining the relative order of the non-zero elements.

For example, given nums = [0, 1, 0, 3, 12], after calling your function, nums should be [1, 3, 12, 0, 0].

Note: You must do this in-place without making a copy of the array. Minimize the total number of operations.


With that, here is my code:

/**
 * @param {number[]} nums
 * @return {void} Do not return anything, modify nums in-place instead.
 */
var moveZeroes = function(nums) {
    var i, temp;

    for (i = 0; i < nums.length-1; i++) {
        if(nums[i] === 0) {
            temp = nums.splice(i, 1);
            nums.push(temp[0]);
        }
    }
    return null;
};

The comments at the top of the code sample are provided in their text editor, and led me to believe that I am not supposed to provide any return statement. Though the validator on their site seemed to not want to accept that at all, so I started returning null...

When I log my nums to the console after handling the input, I am seeing the desired result nums = [1, 3, 12, 0, 0]. Regardless my answer keeps getting rejected. I would love to understand what I am doing wrong here, so I can fix it.

I understand this may be a duplicate. I saw other responses dealing with C and Java, but none I saw dealt with JS.


Solution 1:

The problem has nothing to do with the return statement, the issue is your algorithm is wrong.

[0,0,1,2,3] will return [0,1,2,3,0]

When you loop in the positive direction and remove indexes, you skip indexes as the next index slides down to the position you already covered.

You need to loop in the negative direction. Start at the end and go to the start.

for (i = nums.length-1; i>=0; i--) {

Solution 2:

This is an O(n) solution to the problem:

var moveZeroes = function (nums) {
  let count = 0;
  
  for (let i = 0; i < nums.length; i++) {
    if (nums[i] !== 0) {
      nums[count++] = nums[i];
    }
  }

  for (let i = count; i < nums.length; i++) {
    nums[i] = 0;
  }
  
  return nums;
};

Solution 3:

As everyone has already stated: when it says do not return anything, simply do not write a return statement.

However, there is a problem with your code. Use the test case [0,0,1]. If you start at the first element so it moves it to the back of the array, [0,1,0]. Now your loop index is looking at the second element which is 1. you've completely missed the second 0.