2

Given a Javascript object

x = {'a': 123, 'b': 'hello', 'c': NaN, 'd': null, 'e': undefined}

Is it possible to remove all properties that has NaN, null, or undefined using Lodash, or without Lodash but in a similarly readable way?

Tried

_.omitBy(x, _.isNil)

but it did not remove NaN

{a: 123, b: "hello", c: NaN}

Can _.omitBy take multiple parameters in addition to _.isNil?

5 Answers 5

4

Because isNil just checks for the null/undefined value (doc)

Checks if value is null or undefined.

So you also have to check if the value is NaN with _.isNaN.

_.overSome([_.isNil, _.isNaN])

const x = {'a': 123, 'b': 'hello', 'c': NaN, 'd': null, 'e': undefined}

const res = _.omitBy(x, _.overSome([_.isNil, _.isNaN]))

console.log(res)
<script src="https://cdn.jsdelivr.net/npm/[email protected]/lodash.min.js"></script>

Or you could also do that in vanilla JS.

  • Transform the object to array of key-value pairs
  • reject pairs that have falsy value
  • transform the pairs back to object

const x = { a: 123, b: "hello", c: NaN, d: null, e: undefined };

const isNilOrNaN = (val) => val == null || Number.isNaN(val);

const res = Object.fromEntries(
  Object.entries(x).filter(([key, value]) => !isNilOrNaN(value))
);

console.log(res);

Sign up to request clarification or add additional context in comments.

2 Comments

This would also remove 0, empty strings, literal false, and any other falsy values.
@JustinTaddei I've just updated my answer
2

You can use Number.isNaN to detect NaN and value == null to detect null and undefined.

x = {'a': 123, 'b': 'hello', 'c': NaN, 'd': null, 'e': undefined}

const result = Object.keys(x).reduce((acc, key) => {
  if (x[key] == null || Number.isNaN(x[key])) {
    return acc
  }

  return {
    ...acc,
    [key]: x[key],
  }
}, {})

console.log(result)

Comments

1

Using just javascript, you could use Array.filter on an array created with Object.entries then turn it back into an object with Object.fromEntries.

const sourceObj = {
  'a': 123,
  'b': 'hello',
  'c': NaN,
  'd': null,
  'e': undefined,
  'f': 0,
  'g': ''
}

const result = Object.fromEntries(Object.entries(sourceObj).filter(([key, val]) =>
  val != null && !Number.isNaN(val)
))

console.log(result);

Using lodash you could use pickBy, isNaN, and isNil.

const sourceObj = {
  a: 123,
  b: "hello",
  c: NaN,
  d: null,
  e: undefined,
  f: 0,
  g: ""
};

const result = _.pickBy(sourceObj, (value) => {
  return !_.isNaN(value) && !_.isNil(value)
})

console.log(result);
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.20/lodash.min.js" integrity="sha512-90vH1Z83AJY9DmlWa8WkjkV79yfS2n2Oxhsi2dZbIv0nC4E6m5AbH8Nh156kkM7JePmqD6tcZsfad1ueoaovww==" crossorigin="anonymous"></script>

Which one has better readability is debatable.

Comments

0

Use Array.includes will solve many problems like this.

let x = {'a': 123, 'b': 'hello', 'c': NaN, 'd': null, 'e': undefined}

let result =
    Object.fromEntries(
        Object.entries(x).filter(
            v => ![NaN, null, undefined].includes(v[1])))

// result is { a: 123, b: "hello" }
console.log(result)

Comments

0

I did it like this:

const x = {'a': 123, 'b': 'hello', 'c': NaN, 'd': null, 'e': undefined}

const cleaned = _(x).omitBy(_.isNil).omitBy(_.isNaN).value()

console.log(cleaned)
<script src="https://cdn.jsdelivr.net/npm/[email protected]/lodash.min.js"></script>

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.