I have an array of objects:
And I want to remove the object, that has a specific date (2020年09月24日 in this example) in the excluded_dates Array to output the new Array like this:
outcome = [
{
title: '"test1"',
excluded_dates: false,
},
{
title: '"test2"',
excluded_dates: [
{ excluded_date: "2020年09月12日" },
{
excluded_date: "2020年09月17日",
},
],
}
];
For this, I was thinking of using double filtering. I also tried some(), but that is for Arrays, not an Array of Objects.
const data = [
{
title: '"test1"',
excluded_dates: false,
},
{
title: '"test2"',
excluded_dates: [
{ excluded_date: "2020-09-12" },
{
excluded_date: "2020-09-17",
},
],
},
{
title: '"test3"',
excluded_dates: [
{
excluded_date: "2020-09-16",
},
{
excluded_date: "2020-09-24",
},
],
},
];
const outcome = data.filter(function (event) {
if (event.excluded_dates) {
return event.excluded_dates.filter(
(date) => date.excluded_date === "2020-09-24"
);
}
});
console.log(outcome);
This ofcourse doesn't work as expected. What am I'm missing here?
6 Answers 6
Make sure to return true if the object does not have an excluded_dates property. Also, since you are only looking for one date, you can replace your second use of Array.prototype.filter with Array.prototype.some()
const outcome = data.filter((event) => {
return !(
event.excluded_dates && // if there is no `excluded_dates` property, return `true`
event.excluded_dates.some( // otherwise, try to find the date. if found, return `false`
({ excluded_date }) => excluded_date === "2020年09月24日"
)
);
});
Code snippet example:
const data = [{
title: '"test1"',
excluded_dates: false,
},
{
title: '"test2"',
excluded_dates: [{
excluded_date: "2020-09-12"
},
{
excluded_date: "2020-09-17",
},
],
},
{
title: '"test3"',
excluded_dates: [{
excluded_date: "2020-09-16",
},
{
excluded_date: "2020-09-24",
},
],
},
];
const outcome = data.filter((event) => {
return !(
event.excluded_dates &&
event.excluded_dates.some(
({ excluded_date }) => excluded_date === "2020-09-24"
)
);
});
console.log(outcome);
2 Comments
Array.prototype.filter() runs a given function through every element of an array. If the function returns true, it will keep the element in the array. Otherwise, it will remove it from the array.I would use filter:
let data = [
{ index: 0, exclude: ['Monday'] },
{ index: 1, exclude: ['Tuesday', 'Thursday'] },
{ index: 2, exclude: ['Wednesday'] },
];
data = data.filter(el => !el.exclude.includes('Tuesday'));
console.log(data);
// data = { index: 0, exclude: ['Monday'] }, { data: 2, exclude: ['Wednesday'] }
Comments
Return true if event has not the excluded_dates property, because those you'll want to keep in every scenario.
Instead of a nested filter check if every excluded_date in the excluded_dates array is not equal to "2020年09月24日" with the Array.prototype.every method, which returns true or false based if every callback evaluated true or not.
const data = [{
title: '"test1"',
excluded_dates: false,
},
{
title: '"test2"',
excluded_dates: [{
excluded_date: "2020-09-12"
},
{
excluded_date: "2020-09-17",
},
],
},
{
title: '"test3"',
excluded_dates: [{
excluded_date: "2020-09-16",
},
{
excluded_date: "2020-09-24",
},
],
},
];
const outcome = data.filter(function(event) {
if (event.excluded_dates) {
return event.excluded_dates.every(
(date) => date.excluded_date !== "2020-09-24"
);
}
return true;
});
console.log(outcome);
Comments
you were at right track, only need to change the condition. Filter always return item where condition is matching. you need to check if excluded_date is false or excluded_date array doesn't contain the date. So in inner filter If we get length 0,it means date is not present in the array and so include in expected output.
const data = [{
title: '"test1"',
excluded_dates: false,
},
{
title: '"test2"',
excluded_dates: [{
excluded_date: "2020-09-12"
},
{
excluded_date: "2020-09-17",
},
],
},
{
title: '"test3"',
excluded_dates: [{
excluded_date: "2020-09-16",
},
{
excluded_date: "2020-09-24",
},
],
},
];
const outcome = data.filter(event => (!event.excluded_dates || event.excluded_dates.filter(
(date) => date.excluded_date === "2020-09-24"
).length == 0))
console.log(outcome);
Comments
You were on the right track. You can even use some() for the excluded_dates array. Here is a working function
data.filter((d) => {
if (Array.isArray(d.excluded_dates)) {
return d.excluded_dates.some((date) => date.excluded_date === '2020-09-24');
}
return true;
});
Comments
Tried using Foreach and filter operators
const data = [
{
title: '"test2"',
excluded_dates: [
{ excluded_date: "2020-09-12" },
{
excluded_date: "2020-09-17",
},
],
},
{
title: '"test3"',
excluded_dates: [
{
excluded_date: "2020-09-16",
},
{
excluded_date: "2020-09-24",
},
],
},
];
data.forEach(function(item, idx) {
item.excluded_dates.filter(function(item1) {
if( item1.excluded_date === "2020-09-24" ) {
return data.pop(idx);
}
});
});
console.log(data);