Reputation: 425
Is there some elegant way of filtering out falsey properties from this object with lodash/underscore? Similar to how _.compact(array)
removes falsey elements from arrays
so from
{
propA: true,
propB: true,
propC: false,
propD: true,
}
returning
{
propA: true,
propB: true,
propD: true,
}
Upvotes: 39
Views: 73923
Reputation: 71
As partially mentioned in a comment, ES6 provided Object.entries() and in 2019 Object.fromEntries().
Allowing:
Object.fromEntries(Object.entries(obj).filter(([key, value]) => ...))
Ex:
const obj = {
a: 12,
b: 123,
};
const filteredObj = Object.fromEntries(
Object.entries(obj).filter(
([_, value]) => value > 100
)
);
console.log(filteredObj);
// {b: 123}
Upvotes: 7
Reputation: 33389
Lodash 4.0 has _.pick
, which takes an array of properties, and _.pickBy
which takes a function as an argument and returns an object only containing the keys for which that function returns truthy which is what we want here, so it'd be:
filtered = _.pickBy(obj, function(value, key) {return value;})
Or, since _.pickBy
defaults to using _.identity
as it's second argument, (and that's essentially what we've written above,) it can just be written as:
filtered = _.pickBy(obj);
In underscore and old versions of lodash, there's just a single _.pick
, which has both behaviors of _.pick
and _.pickWith
from v4. So you can do:
filtered = _.pick(obj, function(value, key) {return value;})
Or more succinctly:
filtered = _.pick(obj, _.identity)
Upvotes: 31
Reputation: 892
Another approach
const objFilter = (obj, condition) => {
let newObj = {}
for (const [key, value] of Object.entries(obj)) {
if (condition(value)) {
newObj = { ...newObj, [key]: value }
}
}
return newObj
}
Fire like this:
const newData = objFilter(oldData, (value) => value.marked === false)
Upvotes: 0
Reputation: 27
let temp = {
propA: true,
propB: true,
propC: false,
propD: true,
}
let obj = {}
for(x in temp){
if(temp[x] == true){
obj[x] = temp[x]
}
}
console.log(obj)
Using for-in loop we can achieve it something like this.
Upvotes: 0
Reputation: 121
From lodash 4, we can use pickBy() to get only the value equal to true.
const active = _.keys(_.pickBy(object));
Upvotes: 0
Reputation: 41675
Here are two vanilla javascript options:
A.: Iterate over the object's keys and delete
those having a falsey value.
var obj = {
propA: true,
propB: true,
propC: false,
propD: true,
};
Object.keys(obj).forEach(key => {
if (!obj[key]) delete obj[key];
});
console.log(obj);
See Object.keys()
and Array.prototype.forEach()
B.: Iterate over the object's keys and add truthy values to a new object.
var obj = {
propA: true,
propB: true,
propC: false,
propD: true,
};
var filteredObj = Object.keys(obj).reduce((p, c) => {
if (obj[c]) p[c] = obj[c];
return p;
}, {});
console.log(filteredObj);
See Object.keys()
and Array.prototype.reduce()
Upvotes: 36
Reputation: 21
Unfortunately I cannot direclty comment on the posts above yet, so I create this extra post.
Since Lodash v4 the functionality described above has been moved to _.pickBy. With _.identity
as default you could also change your code to:
var filtered = _.pickBy(obj);
See this JSBin for a working example.
Upvotes: 2
Reputation: 11211
If you're using lodash, I'd recommend something like this:
var object = {
propA: true,
propB: true,
propC: false,
propD: true,
};
_.pick(object, _.identity);
// →
// {
// propA: true,
// propB: true,
// propD: true
// }
The pick() function generates a new object that includes properties that the callback returns truthy for. So we can just use the identity() function as the callback, since it'll just return each property value.
Upvotes: 1