JavaScript 30 – Day 4: Array Cardio 1

Welcome to my recap of Day 4 of the free JavaScript 30 online video course by Wes Bos. In case you really have not yet heard of the course, quickly head over to it and get started right away! 🙂

Please refer to the JavaScript 30 archive for all recap posts.

Objective

Day 4 will (at least try to) make you sweat. 🙂 The task is to really internalize the most prominent JavaScript array functions (i.e., .filter(), .map(), .reduce(), and .sort())—or like Wes called it: the gateway drug to functional programming. 😀

The provided starter files include not more than a single HTML file that again contains three arrays with data to perform our workout on. 🙂 For the sake of better reading, I moved the data into a separate JavaScript file for my fork of the JavaScript 30 repository.

I stopped the video right after the first minute, and jumped right in on the cardio.

Conception

As a disclaimer, I really love array functions—both in JavaScript and PHP—and I am also pretty much up to date when it comes to ES6.

For the individual subtasks, there isn’t really any conception required. It’s always just a single array function, and therefore fairly straightforward.

Implementation

Let’s start with the workout then! 🙂

Filter Inventors

This is my code to filter the list of inventors for those who were born in the 1500’s:

console.log(
    inventors.filter( ( { year } ) => ( 1499 < year && year < 1600 ) )
);

Like for most of the other tasks as well, I am using an arrow function (with implicit return) as callback here. I also make advantage of destructuring, and thus don’t have to reference the year property twice.

Get Inventor Names

Next up, get an array of “firstname lastname” for all of the inventors, here you go:

console.log(
    inventors.map( ( { first, last } ) => `${first} ${last}` )
);

The code, again, makes use of destructuring—this time two properties, and thus variables—and also includes a template string.

Sort Inventors by Birthdate

The third subtask calls for sorting the inventors by their birthdate, oldest to youngest. And I did it like so:

console.log(
    inventors.sort( ( { year: a }, { year: b } ) => ( a - b ) )
);

This time, I am destructuring two inventors, and thus have to rename the variables. So instead of two times year, which wouldn’t work out, of course, I have a and b containing the two birthdates. ES6 is awesome! 😀

Compute Years of Life

Workout number 4 is to compute how many years all the inventors lived. This means that the result is not an array anymore, but a single value. Here is how I went about this:

console.log(
    inventors.reduce( ( sum, { year, passed } ) => ( sum + ( passed - year ) ), 0 )
);

Not much to say about this, right?

Sort Inventors by Years of Life

The fifth subtask is again about sorting. It requires a little more work with the data, but it still fits in a single line:

console.log(
    inventors.sort( ( a, b ) => ( ( a.passed - a.year ) - ( b.passed - b.year ) ) )
);

I decided against destructuring (and renaming!), because in the end the code wouldn’t get any shorter at all. In order to easily understand what is going on, it has to be fairly self-explanatory, for example, like so:

console.log(
    inventors.sort( ( { year: y1, passed: p1 }, { year: y2, passed: p2 } ) => ( ( p1 - y1 ) - ( p2 - y2 ) ) )
);

So, nothing gained here.

Something with Boulevards…?

The comment for the sixth workout caught me off guard. I just didn’t understand what to do here. 😐 I mean, if I had a list of all boulevards, no problem then. But I don’t. And since I didn’t expect to be using AJAX or fetch() or something similar here, I decided to wait for clarification in the video. 🙂

Sort People by Last Name

Number 7, also, surprised me a little. The reason is that the people already are sorted by last name…!? Either I got something wrong here, or the data should be given in another (not alphabetically sorted) order.

Anyway, assuming the data is not sorted, this is how to achieve sorting:

console.log(
    people.sort( ( a, b ) => ( a.split( ',' )[0] > b.split( ',' )[0] ) )
);

I am using .split() to get the individual last name, and then sort based on these.

Count Instances

The last subtask is about generating a tally sheet.

console.log(
    data.reduce( ( sums, item ) => {
        sums[ item ] = ( sums[ item ] || 0 ) + 1;

        return sums;
    }, {} )
);

Starting off with an empty object, each occurrence of an item (i.e., a string) is counted inside the object. This is done by using the string as property name.

By the way, this is the first (and last) one that I realized by using an arrow function with a body (and thus an explicit return). 🙂

Refinement

Having completed the video, I can say that Wes doesn’t use destructuring. I mean, maybe he just doesn’t know any better…?! Just kidding. I learned about destructuring in Wes’s awesome ES6 for Everyone course that I just cannot recommend enough! 😀

Also, in my sort callbacks, I neither use an if statement, nor a “ternarary” [sic] operator. (BTW, I do believe Wes meant a ternararary. 😀 ) Instead, I simply subtract one value from the other (the order depends on whether I want to sort in ascending or descending order).

Alrighty! Having peeked into the boulevard thing, I now know this should be done on the according Wikipedia page, in the console. 🙂 I stopped the video again, and came up with the following code:

Array.from( document.querySelector( '.mw-category' ).getElementsByTagName( 'a' ) )
    .map( ( el ) => el.text )
    .filter( ( name ) => ( 0 <= name.indexOf( 'de' ) ) );

Comparing with what Wes did, you can see I used .getElementsByTagName() to query all the anchor tags, I chose to use .text (and not .textContent), and I checked the result of .indexOf() being greater or equal to 0, which would be the index of the first character. Since .includes(), however, already returns a Boolean value, I really like it better. 🙂 The refined code now looks like this:

Array.from( document.querySelector( '.mw-category' ).getElementsByTagName( 'a' ) )
    .map( ( el ) => el.text )
    .filter( ( name ) => name.includes( 'de' ) );

Following Wes’s code for sorting the already alphabetically sorted array of people, I come to the conclusion that Wes sorted that already alphabetically sorted array alphabetically. Huh? 😀

Live Demo

Want to see this in action? Well, here is a live demo. 🙂

Make sure to have a look at your console, though. 😉

Retrospection

I really liked this! And I just can’t wait for Array Cardio 2 to be on the schedule. 🙂

To be honest, I didn’t learn much new here, but like I said, I am pretty used to be using these things on a regular basis.

And You?

JavaScript 30 is free! So, unless you already did this on your own, what’s your reason not to? 🙂

Leave a Reply

Your email address will not be published. Required fields are marked *