I am learning about pointfree functions and am trying to implement this recursive null remover in that style.
Works, but is not pointfree:
function removeNulls(obj) {
return R.ifElse(
R.either(R.is(Array), R.is(Object)),
R.pipe(
R.filter(R.pipe(R.isNil, R.not)),
R.map(removeNulls)
),
R.identity
)(obj)
}
module.exports = removeNulls
The following is my non-functioning attempt at it:
const removeNulls = R.ifElse(
R.either(R.is(Array), R.is(Object)),
R.pipe(
R.filter(R.pipe(R.isNil, R.not)),
// throws `ReferenceError: removeNulls is not defined`
R.map(removeNulls)
),
R.identity
)
Luckily JavaScript has resources to deal with its lack of laziness. So, it's completely possible to declare a recursive pointfree solution by using lambda functions in the following way: a => f(a)
. Just replace R.map(removeNull)
with R.map(a => removeNull(a))
.
const removeNulls = R.ifElse(
R.either(R.is(Array), R.is(Object)),
R.pipe(
R.filter(R.pipe(R.isNil, R.not)),
R.map(a => removeNulls(a))
),
R.identity
)
In your case, I'll recommend you to use R.reject
which is the oposite to R.filter
. Since you are negating the predicate, R.filter(R.pipe(R.isNil, R.not))
is equal to R.reject(R.isNil)
const removeNulls = R.ifElse(
R.either(R.is(Array), R.is(Object)),
R.pipe(
R.reject(R.isNil),
R.map(a => removeNulls(a))
),
R.identity
)
Finally, this function has the following structure ifElse(predicate, whenTrue, identity)
which is equal to when(predicate, whenTrue)
const removeNulls = R.when(
R.either(R.is(Array), R.is(Object)),
R.pipe(
R.reject(R.isNil),
R.map(a => removeNulls(a))
)
)
Simplified version, regarding the comment from Declan Whelan, since arrays are Object
const removeNulls = R.when(
R.is(Object),
R.pipe(
R.reject(R.isNil),
R.map(a => removeNulls(a))
)
)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With