Seek and Destroy

In this freeCodeCamp algorithm we are provided with an initial array arr followed by additional arguments. Our goal is to remove all elements from arr that are the same value as the additional arguments provided.

Requirements

  • destroyer([1, 2, 3, 1, 2, 3], 2, 3) should return [1, 1]
  • destroyer([1, 2, 3, 5, 1, 2, 3], 2, 3) should return [1, 5, 1]
  • destroyer([3, 5, 1, 2, 2], 2, 3, 5) should return [1]
  • destroyer([2, 3, 2, 3], 2, 3) should return []
  • destroyer(["tree", "hamburger", 53], "tree", 53) should return ["hamburger"]
  • destroyer(["possum", "trollo", 12, "safari", "hotdog", 92, 65, "grandma", "bugati", "trojan", "yacht"], "yacht", "possum", "trollo", "safari", "hotdog", "grandma", "bugati", "trojan") should return [12,92,65]

Ok. So this one is a little strange. We're provided an array named arr AND additional arguments but only one variable is being passed as an argument to our function? Hmm...🤔

NOTE: We must use the arguments object for this one

Let's take a peek at the Arguments Object over at the Mozilla Developer Network.

Psuedocode

// Set variable for array which is at index 0 of arr

// Loop through items in arr0
    // With loop of arr0, loop through all items in arguments object
    // If item in arr0 matches item in arguments object, remove it from arr0
    // Set iteration in arguments loop back to 0 so it starts back at index 0 of arr0
    
    // Return arr0

Solving the Algorithm

Setting up the function

In this function, we accept one big argument, arr which is made up of smaller 'sub-arguments' - an array and then some additional numbers that we must remove from that array if they match these additional numbers. Stay with me here.

function destroyer(arr) {
    
}

Getting the Array from Index 0 of arr

After reading up on the Arguments Object you should feel somewhat confident in being able to get that array which will always be at index zero of the argument arr that we pass to our function. Let's try it out.

function destroyer(arr) {
    var arr0 = arguments[0]; // Get the array that is passed as the first argument
    
    console.log(arr0);
    
}
destroyer([3, 5, 1, 2, 2], 2, 3, 5); // Outputs [3, 5, 1, 2, 2]

Try this the code snippet in your browser console.

Setting Up the Loop Within the Loop

function destroyer(arr) {
    var arr0 = arguments[0];

    for (var i = 0; i < arr0.length; i++) {
		for (var j = 0; j < arguments.length; j++) {
                console.log('arr0[i]', arr0[i]);
				console.log('arguments[j]', arguments[j])
            }
		}
    }
//     return arr0
destroyer([3, 5, 1, 2, 2], 2, 3, 5)

// NOTE: You will see what exactly is going on in the loop within the loop.
// Sometimes this can seem a little crazy, but hopefully it helps
// you visualize what exactly is going on within this nested for-loop

Try this the code snippet in your browser console.

Remove Any Items from arr0 That Match Other Args

From here we need to check if an item from arr0 matches any other item from the arguments object. If you've followed along with any of the earlier freeCodeCamp algorithm walkthroughs, you'd probably guess that we can use the Array.splice() method for this one.

function destroyer(arr) {
    var arr0 = arguments[0];
    
    for (var i = 0; i < arr0.length; i++) {
		for (var j = 0; j < arguments.length; j++) {
			if (arr0[i] == arguments[j]) {
            arr0.splice(i, 1);
            }
		}
    }
    return arr0;
}
destroyer([3, 5, 1, 2, 2], 2, 3, 5); // Outputs [1, 2]

Debugging 🕷

Hmmm...🤔 Why didn't this end up working? Well, for starters, let's try our hand at the Chrome Debugger so we can take a closer look.

Paste this code below into your Chrome console

function destroyer(arr) {
    var arr0 = arguments[0];
    
    debugger;
    
    for (var i = 0; i < arr0.length; i++) {
		for (var j = 0; j < arguments.length; j++) {
			if (arr0[i] == arguments[j]) {
            arr0.splice(i, 1);
            }
		}
    }
    return arr0;
}
destroyer([3, 5, 1, 2, 2], 2, 3, 5); // Outputs [1, 2]

NOTE: Notice that there's now a line of code, debugger; towards the top of the function

Once you've done that, the 'sources' tab in your Chrome dev tools should open up and look something like this:

The debugger is such an awesome tool. It allows us to step through our code piece by piece, essentially in slow motion.

In order to step through our code you can click on the 'step over next function call' button that looks like this:

You might notice that our iterator, j, which is in the arguments loop gets thrown out of whack after the 3 and the 5 from arr0 get spliced out of the array.

Solution

What might we be able to do in order to reset j after everytime it has found a number to splice from arr0?

This one's a pretty quick fix once we knew where to look, all thanks to our new friend, the debugger.

Let's make sure to reset j to 0 after every successful splice.

function destroyer(arr) {
    var arr0 = arguments[0];

    for (var i = 0; i < arr0.length; i++) {
		for (var j = 0; j < arguments.length; j++) {
			if (arr0[i] == arguments[j]) {
            arr0.splice(i, 1);
			j = 0; // Reset j to zero after it has a found a number to slice
            }
		}
    }
    return arr0
}
destroyer([3, 5, 1, 2, 2], 2, 3, 5) // Should return [1]

Final Thoughts

Hopefully you found this to be a helpful walkthrough on this freeCodeCamp algorithm on how to seek and destroy numbers in an array!

Shoot me an email at tim@timwheeler.com with any questions and if you enjoyed this, stay tuned and subscribe below! 👇