Second day of the Dev Advent Calendar 2021 and new puzzle to solve. Santa’s elves have managed to find Rudolf the reindeer lost in the forest. Back in the village they need to warm up with a hot cup. But the Elf Coffee Shop menu is confusing. Maybe we need to help the elf bartender rewrite the menu.

The puzzle: Elf Coffee Shop 🧝🥤

Today’s problem is about joining two arrays of objects. It also concerns their ordering. Today’s puzzle is also quite simple but I had to deepen some of my knowledge. I haven’t had time to test various solutions, so I’m not ruling out that there is a smarter way. But no more chatter and let’s start with the puzzle.

Sort an array of objects: alphabetical order

I immediately tackle the problem of sorting. Why? Because I suspect it’s quicker to sort two small arrays than to sort a much larger array. So I start by alphabetizing the drinks list.

Before starting I recommend reading a post from Javascript Tutorial: Sorting Array Elements. And, of course, the documentation of the Array.prototype.sort() method.

The first step is to directly sort the drink list based on the “name” property. So I check if the name of one comes before the name of the other based on the alphabet.

The first problem that may arise concerns the difference between upper and lower case letters. If it is not difficult for us humans to understand that a === A for Javascript there are some problems. It is therefore convenient to convert all names to uppercase (or lowercase) letters.

Fine, but this way I’m going to change the menu itself. After that it will be difficult to get a menu with the names written correctly. To solve the problem I don’t directly modify the array but I copy the names in some variables:

There is another problem: the sort() method directly modifies the order of the original array. Personally I prefer to leave everything unchanged. I follow Ramon Balthazar’s advice: use shuffledArray.slice().sort(). This way I get a new array without changing the original one:

Sort an array of objects: numerical order

After you have sorted your drinks, it’s time to move on to the various custom flavors. Instinctively I can think of using a similar function, replacing the name property with the price property:

However, there is a particular case that is missing from this list of ingredients: the drink without extra flavor.

I think the quickest way to deal with this case is to add the “flavor: undefined” with price 0 to the list. I add it to the beginning of the sorted list with the unshift() method

Combining drinks and flavors on a menu

Now that I have two sorted arrays (sortedDrinks and sortedFlavors) I can start combining ingredients and flavors. I could use two nested for loops. Or use the map() method:

But there is a problem: the result is an array containing several arrays, one for each drink. The puzzle requires an array like this:

I can use the flat() or Array.prototype.flatMap() method:

Well, Santa’s elves can be satisfied. Through this solution they can finally order what they want from a convenient menu. Now the time has come for me to drink a nice hot herbal tea.