I have an Array of Geography-Location-Objects of this kind:
let markers = [
{
"markerOffset": 10,
"name": "Plantation",
"coordinates": ["9.85804","53.5233"]
},
{
"markerOffset": 10,
"name": "Roasting",
"coordinates": ["29.85804","50.5233"]
},
{
"markerOffset": 10,
"name": "Packaging",
"coordinates": ["29.85804","50.5233"]
},
{
"markerOffset": 10,
"name": "Harbour",
"coordinates": ["21.85804","51.5213"]
},
]
How can I filter the array to remove duplicate objects with the same coordinates (such as element 2 and 3) and only leave one entry with the coordinates.
A Set wont work propably because of the differing name:
attribute
CodePudding user response:
You'll need to loop through the markers
array add unique markers (by their coordinates) to a new array. This second array will be used to compare the next marker in the loop.
const markers = [
{
markerOffset: 10,
name: "Plantation",
coordinates: ["9.85804", "53.5233"],
},
{
markerOffset: 10,
name: "Roasting",
coordinates: ["29.85804", "50.5233"],
},
{
markerOffset: 10,
name: "Packaging",
coordinates: ["29.85804", "50.5233"],
},
{
markerOffset: 10,
name: "Harbour",
coordinates: ["21.85804", "51.5213"],
},
];
const filteredMarkers = [];
for (let i = 0, length = markers.length; i < length; i ) {
let duplicate = false;
for (let j = 0, length = filteredMarkers.length; j < length; j ) {
const [lat1, lon1] = markers[i].coordinates;
const [lat2, lon2] = filteredMarkers[j].coordinates;
if (lat1 === lat2 && lon1 === lon2) {
duplicate = true;
break;
}
}
if (!duplicate) {
filteredMarkers.push(markers[i]);
}
}
console.log(filteredMarkers);
CodePudding user response:
Simple compare and build a new array. This doesn't care about the name attribute and just uses the first one that comes along
let markers = [
{ "markerOffset": 10, "name": "Plantation", "coordinates": ["9.85804","53.5233"] },
{ "markerOffset": 10, "name": "Roasting", "coordinates": ["29.85804","50.5233"] },
{ "markerOffset": 10, "name": "Packaging", "coordinates": ["29.85804","50.5233"] },
{ "markerOffset": 10, "name": "Harbour", "coordinates": ["21.85804","51.5213"] },
]
let results = [];
markers.forEach(marker => {
if(!results.find(m => m.coordinates[0] === marker.coordinates[0] && m.coordinates[1] === marker.coordinates[1] )) results.push(marker);
})
console.log(results);
CodePudding user response:
A nice simple way is to use findIndex
using the coordinates, you can just toString
these to make the find even easier, use this in a filter, and if the index is the same it's the first of a duplicate or not a duplicate.
eg.
const markers = [
{
markerOffset: 10,
name: "Plantation",
coordinates: ["9.85804", "53.5233"],
},
{
markerOffset: 10,
name: "Roasting",
coordinates: ["29.85804", "50.5233"],
},
{
markerOffset: 10,
name: "Packaging",
coordinates: ["29.85804", "50.5233"],
},
{
markerOffset: 10,
name: "Harbour",
coordinates: ["21.85804", "51.5213"],
},
];
console.log(
markers.filter(
(m,ix) => markers.findIndex(c =>
c.coordinates.toString() ===
m.coordinates.toString()) === ix)
);
Bonus, if you wanted the last of a duplicate, you can just change findIndex
to findLastIndex
CodePudding user response:
Another way to make an array unique by a certain property:
const markers=[{markerOffset:10,name:"Plantation",coordinates:["9.85804","53.5233"]},{markerOffset:10,name:"Roasting",coordinates:["29.85804","50.5233"]},{markerOffset:10,name:"Packaging",coordinates:["29.85804","50.5233"]},{markerOffset:10,name:"Harbour",coordinates:["21.85804","51.5213"]}];
const uniqByCoords = Object.values(markers.reduce((acc, market) => {
acc[String(market.coordinates)] ??= market; //return first market item in array as uniq.
// If you need the last one replace ??= to =
return acc;
}, {}));
console.log(uniqByCoords);
.as-console-wrapper { max-height: 100% !important; top: 0; }