JavaScript Patterns β€” Wrangling arrays like a boss, with Array#reduce πŸ‘Š

    Write your comment

    Start writing...

    • Sort By :
    • Popular
    • Recent

    This comment has received 1 appreciation.

    Hi there. Nice article! Indeed, reduce is always a better choice than more generic methods, like forEach or map/filter combinations for cases when you need to generate one single value or object. And more importantly, it improves readability of your code, as your fellow developer knows right aways what's going on.For this specific case, I have a different approach for you:

    var emails = nodes.reduce(function(store, node) { 
        return node.followers.reduce(function(store, follower) { 
            follower.email && (store[follower.email] = true); 
            return store; 
       }, store); 
    }, {});
    
    console.log(Object.keys(emails));
    

    https://jsfiddle.net/epp9zwj0/6/ A bit shorter)

    Cool! I think it can have an additional benefit in case it's necessary to keep emails in the same order as nodes. While object properties also preserve insertion order, it is not guaranteed.

    Write a reply...

    This comment has received 1 appreciation.

    You got me thinking this morning, so I was looking for potential optimizations. I'm far from a guru on optimizations but I thought I'd take your idea and extend it into the followers node. forEach is notably a slow function, so I thought why not use a reducer?

    https://jsperf.com/multi-reducer-comparison

    Looks like a clear win, and we increase readability, separate the concerns a bit, and made each reducer a little more testable.

    Cheers!

    Brilliantly done! :) πŸ‘

    Write a reply...

    For what it's worth I actually think you older code is more readable, here is how I would have improved it:

    const followers = (nodes) => {
      return _(nodes)
        .flatMap( node => node.followers)
        .filter( follower => follower.email)
        .map( follower => follower.email)
        .uniq()
    }
    

    I think some would disagree with this, but I personally favour readability in code and I think your old code is easier to reason about. As a bonus, the time required to complete this also faster.

    Ah ha, thank you sir!

    Write a reply...

    getSetOfFollowerEmails doesn't return anything. Good article. Array#reduce is underused. If I see one more var isTrue; and a for loop, I'm going to lose it.

    Hahah, I hear you! And, thank you! Added the missing return. :)

    Write a reply...

    About "one reduce to rule them all" - I recommend to have a look at Lodash chaining https://lodash.com/docs/4.17.4#lodash

    Write a reply...

    #2's reducer functions needs to return acc because acc.push returns the pushed item:

    const squaresOfNumbers = numArray => numbers.reduce(
        (acc, item) => {
           acc.push(item * item);
            return acc;
        },
        []
    );
    

    Why not just use concat instead of push ? make its nice and compact and easy to follow along:

    const squaresOfNumbers = numArray => numArray.reduce((acc, item) => acc.concat(item * item), [])
    
    Write a reply...

    I personally feel that in this case the improved code can be more readable and doesn't need any other libraries by using full es6 potential

    nodes
    .map(node => node.followers.map(user => user.email))    // get all emails in a format [['abc@abc.com', 'ijk@ijk.com'...], ['abc@abc.com', ...], ...]
    .reduce((emails, result) => [...emails, ...result], []) // flatMap like function, flat all the arrays into one
    .filter((email, i, self) => self.indexOf(email) === i)  // get all uniq items
    .filter(mail => mail)                                   // remove undefined or null
    

    https://jsfiddle.net/ae1nof9p/

    There's an error in example 2 for rewriting map function, it should be:

    const squaresOfNumbers = numArray => numArray.reduce(
    
    Write a reply...

    Never miss a story from Sai Kishore Komanduri,
    when you sign up for Hashnode. Learn more

    loading ...