I have the following data structure that i receive from the api:
[
{
id: '10000844',
text_id: '10000844-01',
},
{
id: '10000844',
text_id: '10000844-02',
},
{
id: '12000844',
text_id: '12000844-03',
},
{
id: '12000844',
text_id: '12000844-07',
},
{
id: '12000814',
text_id: '12000844-07',
},
{
id: '12002812',
text_id: '12000844-07',
},
{
id: '12000814',
text_id: '12000844-08',
},
]
The perfect outcome of cleaning the code would be this result, basically returning only the first found id:
[
{
id: '10000844',
text_id: '10000844-01',
},
{
id: '12000844',
text_id: '12000844-03',
},
{
id: '12000814',
text_id: '12000844-07',
},
{
id: '12002812',
text_id: '12000844-07',
},
]
But currently it only returns the last found duplicate in a unique array, with the current code:
let uniqueArray = [...new Map(data.map(item =>
[item.id, item])).values()];
You can use Object.values() and reduce() same as :
const data = [
{
id: '10000844',
text_id: '10000844-01',
},
{
id: '10000844',
text_id: '10000844-02',
},
{
id: '12000844',
text_id: '12000844-03',
},
{
id: '12000844',
text_id: '12000844-07',
},
{
id: '12000814',
text_id: '12000844-07',
},
{
id: '12002812',
text_id: '12000844-07',
},
{
id: '12000814',
text_id: '12000844-08',
},
]
const result = Object.values(
data.reduce((res, {id, text_id}) => {
res[id] ??= {id, text_id}
return res
}, {})
)
console.log(result)
Update with ??= document
The logical nullish assignment (x ??= y) operator only assigns if x is nullish (null or undefined).
You can do it like this:
const arr = [
{
id: '10000844',
text_id: '10000844-01',
},
{
id: '10000844',
text_id: '10000844-02',
},
{
id: '12000844',
text_id: '12000844-03',
},
{
id: '12000844',
text_id: '12000844-07',
},
{
id: '12000814',
text_id: '12000844-07',
},
{
id: '12002812',
text_id: '12000844-07',
},
{
id: '12000814',
text_id: '12000844-08',
},
];
const unique = [];
const visited = new Set();
for(let i = 0; i < arr.length; ++i){
if(!visited.has(arr[i].id)){
unique.push(arr[i]);
visited.add(arr[i].id);
}
}
console.log(unique);
Concept
Loop through all the objects in the data and check if the id is found in result array. If not found then push it into the result array; otherwise, skip it.
Code
const data = [{
id: '10000844',
text_id: '10000844-01',
},
{
id: '10000844',
text_id: '10000844-02',
},
{
id: '12000844',
text_id: '12000844-03',
},
{
id: '12000844',
text_id: '12000844-07',
},
{
id: '12000814',
text_id: '12000844-07',
},
{
id: '12002812',
text_id: '12000844-07',
},
{
id: '12000814',
text_id: '12000844-08',
},
];
let result = [];
let found;
data.forEach(d => {
found = false;
result.forEach(r => {
if (!found && r.id === d.id) found = true;
})
if (!found) result.push(d);
});
console.log(result);