PHP Boolean Breakdown

August 3, 2007

If you’ve used PHP even a little, you’ve probably used something like this in your code:

$result = mysql_query($sql) or die(mysql_error());

At first glance, this statement doesn’t look like it should work because there’s two completely different things, $result = mysql_query($sql) and die(mysql_error()), in a single statement. What’s happening is that the PHP engine is trying to execute the mysql_query($sql), and that function either returns the result of the query, or it fails. If it fails, the PHP engine processes the die(...); command.

Ok, so that’s not quite how it works. There’s two features of PHP at work here that don’t get talked about enough: everything has a boolean value, and short-circuiting expressions.

Everything has a boolean value?

Yes, everything. Any integer, string, float, and function has a boolean value. For integers, if the value is non-zero, the boolean value is true, and the same is true for floats. For strings, it’s a non-empty calculation. That means that a space (‘ ‘) evaluates to true, while an empty string, (‘’), is false. In the case of functions, it’s boolean value is the return value of the function, cast to boolean. When functions don’t return anything, they equate to false. Objects also have a boolean value, but as far as I can tell it’s always true as long as the object exists.

But you already knew that, right?

The boolean feature of PHP gets talked about a lot. Sometimes, I see code that looks like

if(!isset($var) || empty($var)) return false;

when return trim($var); would work just as well. So it’s worth saying again that PHP makes boolean calculations easy.

If we look at our statement again, $result = mysql_query($sql) or die(mysql_error());, and keep in mind that functions can be evaluated as booleans, we can change the statement to look like this: $result = ($one || $two);. The original statement is actually a boolean expression. Yes, you read that correctly. That’s how PHP rolls.

Short circuit? Isn’t that a movie?

Yes, but in programming it refers to a kind of intelligence in the processing engine when dealing with boolean expressions. For example, if you have a string of values connected by __or__s, if any single one of those values evaluates to true the entire statement is going to be true. In the case of values connected with __and__s, if any single one is false the entire statement will be false. When the processing engine encounters one of those situations, it stops processing the expression, because it already knows the outcome.

Looking back to our original statement, we can see that if the mysql_query($sql) portion of the statement succeeds, the rest of the statement is ignored. The variable $result is actually the value of the expression, but because the expression is stopped after one call, the value of the first statement is assigned to the variable. If the mysql_query(...) statement fails, the rest of the statement is executed, and the script dies. If you could examine the value of $result after the second call, you could see that it has a boolean value. In this case, it would still be false, but if we substituted something other than die() into the expression we would see a different result, as long as the second expression returned a boolean value.

In theory, you could chain as many function calls as you like into an expression like this, but I’ve found that it gets really confusing and results are often unexpected. It’s probably a good idea not to put more than two of these together. Also, there’s a potential gotcha in this kind of structure: if you encapsulate the expression in parenthesis, the value of $result is the value of the expression, but otherwise it’s the value of the first call’s return value.

What all this means for you

Remember that everything has a boolean value in PHP, and don’t use two checks when one will do. Also, short-circuiting can work wonders for your application control structure if used properly. And it can also help your if statements if you remember that evaluation stops on true if the entire structure is or’s and false if everything is and’s.