For example if one has the following 2D array (arranged to be [[key, value], [key, value]]):
var input_array = [
["one", "stuff"],
["two", "things"],
["two", "more things"],
["three", "stuff"],
["one", "something"],
["one", "stuff"],
["two", "more things"],
["three", "more stuff"]
]
What is a minimal and efficient way using what ES5/6 has to offer (as oppose to for loops with counters) to create an output object with array values that get rid of the duplicate pairs and sort the array values in alphabetical order:
var output_obj = {
"one": ["something", "stuff"],
"two": ["more things", "things"],
"three": ["more stuff", "stuff"]
}
This can be as concise as a single line reduce using logical nullish assignment (??=), adding elements to a Set()
to handle duplicates, and then iterating the resulting Object.keys()
to convert the Set
s to arrays using spread syntax while also sorting them.
const input = [["one", "stuff"], ["two", "things"], ["two", "more things"], ["three", "stuff"], ["one", "something"], ["one", "stuff"], ["two", "more things"], ["three", "more stuff"]];
const
output = input.reduce((a, [k, v]) => ((a[k] ??= new Set()).add(v), a), {});
Object.keys(output).forEach(k => output[k] = [...output[k]].sort());
console.log(output)
or if you need to avoid logical nullish assignment for compatibility...
const input = [["one", "stuff"], ["two", "things"], ["two", "more things"], ["three", "stuff"], ["one", "something"], ["one", "stuff"], ["two", "more things"], ["three", "more stuff"]];
const
output = input.reduce((a, [k, v]) => ((a[k] = a[k] || new Set()).add(v), a), {});
Object.keys(output).forEach(k => output[k] = [...output[k]].sort());
console.log(output)