4 ms·
The "||" idiom is popular in many languages, but keep in mind that it skips not just NULL (nil) values! It also skips otherwise perfectly desirable values like
by vog 15y ago
The "||" idiom is popular in many languages, but keep in mind that it skips not just NULL (nil) values! It also skips otherwise perfectly desirable values like FALSE, 0 (zero), or "" (empty string).
In SQL there is the handy COALESCE function [1] which does exactly what I want in this case: It simply returns the first non-NULL value of its arguments, even if it is FALSE, 0 or "".
def get_cached_user(user_id = nil, username = nil)
user = coalesce(
cache.get_user_by_id(user_id),
cache.get_user_by_username(username),
db.get_user_by_id(user_id),
db.get_user_by_username(username)
)
if user.nil? raise ValueError('User not found')
cache.set_user(user, user.id, user.username)
return user
end
I always wonder why none of the other programming languages provide a handy COALESCE function/operator out of the box. That way, they wouldn't encourage bug-provoking hacks such as abusing the "||" operator.
Of course you can always implement your own COALESCE function, but that won't provide the nice short-circuit ability. So this is only feasible in languages with macros (e.g. Lisp), or languages which are lazy-evaluated (e.g. Haskell).
All other languages should either provide a COALESCE function/operator, or a sane alternative to "||" which skips only NULL values and nothing else.
[1] http://www.postgresql.org/docs/9.1/static/functions-conditional.html#FUNCTIONS-COALESCE-NVL-IFNULL http://www.postgresql.org/docs/9.1/static/functions-conditio...
- skrebbel 15y agoC#'s ?? operator does exactly that. `x ?? y` returns y iff x is null. In daily practice, I've hardly ever used it. I use early returns all the time, though, and the code becomes very nice and readable.
- cytzol 15y ago> All other languages should either provide a COALESCE function/operator, or a sane alternative to "||" which skips only NULL values and nothing else. In Ruby, only nil and false are false, so you can use || to catch 0s and empty strings. In Perl, 0s and empty strings are false, but there's the // operator (as well as the || or or operators) that catches the first defined value. I'm not sure if this is something specific to the database framework that you're using - sorry if you know all that already.
- vog 15y ago> In Ruby, only nil and false are false, so you can use || to catch 0s and empty strings. But there's still trouble with things like boolean configuration variables ... > In Perl [...] there's the // operator Thanks for mentioning that! [1] The // operator is indeed a clean operator, almost equivalent to COALESCE. So we have Perl and SQL. Any other language with such an operator? [1] http://perldoc.perl.org/perlop.html#C-style-Logical-Defined-Or http://perldoc.perl.org/perlop.html#C-style-Logical-Defined-...