Often in PHP, I see:
$result = mysql_query($query) or die();
Coming from python, I know why this should work, because or
returns the first value if it is true in a boolean context, and the second value otherwise (see this).
But when I try the above technique in PHP in another context, for example something like:
$name = "John Doe";
echo $name or "Anonymous";
The or
doesn't return the first value ("John Doe"), it returns 1.
Why does this work in the mysql_query() result case, but not in other cases? Is it bad to use in a mysql_query() case (ignore the fact that I am not returning a useful error to the user)?
die() function in PHP The die() function prints a message and exits the current script.
Prepend functions with the '@' symbol to suppress certain errors, as opposed to turning off all error reporting. PHP supports one error control operator: the at sign (@). When prepended to an expression in PHP, any error messages that might be generated by that expression will be ignored.
?> Note: The output for the above program will be an empty screen because it is similar to exit(), die() can print only string values. The exit() method is only used to exit the process. The die() function is used to print the message.
PHP supports the @ error control operator (also called STFU operator with mixed feelings), that suppresses errors just for the expression that immediately follows. For example, the unlink function emits a warning if the file does not exist, and calling it with the @ operator can suppress these errors.
In PHP, variable assignment (the equals sign) and functions both take precedence over the or
operator. That means a function gets executed first, then the return value of the function is used in the or
comparison. In turn when you use two values/variables together with an or
operator, it compares the two values first then returns a Boolean value.
Therefore, the order of evaluation in this example is:
$result = mysql_query($query) or die();
mysql_query($query)
Returns either a result set for DQL queries such as SELECT
, or a Boolean value for DDL, DML or DCL queries such as CREATE
, DROP
, INSERT
, UPDATE
, DELETE
and ALTER
.
$result = mysql_query($query)
The result of this query execution is assigned to the variable $result
.
$result /* = ... */ or die();
If it's either a result set or true
, it's considered true (aka "truthy") so the or
condition is satisfied and the statement ends here. Otherwise the script would die()
instead.
echo
is a language construct and therefore doesn't actually return a value, so it doesn't run like a function before the or
comparison is made.
As $name or "Anonymous"
is always true because the string "Anonymous"
is non-empty and therefore truthy, the echo
implicitly converts true
to 1
, hence that output.
The order of evaluation in this example is:
$name = "John Doe";
echo $name or "Anonymous";
$name = "John Doe";
Pretty straightforward — assigns the string John Doe to $name
.
$name or "Anonymous"
PHP discovers that $name
contains the string John Doe, so what ends up being evaluated is the following:
"John Doe" or "Anonymous"
Since at least one string is non-empty here, it's considered truthy and the condition is satisfied. This evaluation then returns true
.
echo true /* $name or... */;
Converts true
to 1
and prints the number 1.
The reason actually occurred to me shortly after asking the question. It's about operator precedence. The =
happens before the or
, so:
$result = mysql_query($query) or die();
is equivalent to:
($result = mysql_query($query)) or die();
not:
$result = (mysql_query($query) or die());
as it would be in Python. So this:
$a = false or true;
will set $a
to false, not true, which is bound to catch me out at some point in the future.
Why should or
return anything? or
is a normal boolean operator. $a or $b
is true
if either $a
or $b
evaluates to true
and false
otherwise.
The difference between ||
and or
is, that or
has a lower operator precedance, even lower than =
. This is why
$result = mysql_query($query) or die();
is same as
($result = mysql_query($query)) or (die());
whereas
$result = mysql_query($query) || die();
is same as
$result = (mysql_query($query) || die());
In your case
echo $name or "Anonymous";
gets
(echo $name) or ("Anonymous");
What you are looking for probably is the ternary operator:
echo $name ?: 'Anonymous';
The above will work as of PHP 5.3, if you have only PHP 5.2 use:
echo $name ? $name : 'Anonymous';
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