PHP Shorthand if
"Shorthand if" refers to compact ways of writing simple decisions: Form Syntax Purpose Ternary operator condition ? valueIfTrue : valueIfFalse Choose between two values Short ternary ("Elvis") value ?
"Shorthand if" refers to compact ways of writing simple decisions:
| Form | Syntax | Purpose |
|---|---|---|
| Ternary operator | condition ? valueIfTrue : valueIfFalse | Choose between two values |
| Short ternary ("Elvis") | value ?: fallback | Use a value unless it is falsy |
| Null coalescing | value ?? fallback | Use a value unless it is null or missing |
One-line if | if (condition) statement; | Run one statement (not recommended) |
The most important of these is the ternary operator, which this lesson covers in depth. The null coalescing operator has its own lesson (Null Coalescing Operator).
The Ternary Operator ?:
What It Is
In simple terms: The ternary operator is a one-line if...else that produces a value: "if this is true, use A; otherwise, use B".
Technically: ?: is the only operator in PHP with three operands (hence ternary). It evaluates the condition, then evaluates and returns only one of the other two expressions.
Syntax
$result = condition ? valueIfTrue : valueIfFalse;
Example
<?php
$age = 20;
$label = $age >= 18 ? 'Adult' : 'Minor';
echo $label;
Output
Adult
Equivalent if...else
<?php
$age = 20;
if ($age >= 18) {
$label = 'Adult';
} else {
$label = 'Minor';
}
echo $label;
Both versions produce the same result. The ternary version is shorter and keeps the assignment on one line, which makes it ideal when the only thing each branch does is produce a value.
Why the Ternary Operator Is an Expression
if...else is a statement: it controls which code runs. The ternary operator is an expression: it produces a value. That means it can be used anywhere a value is expected — in assignments, function arguments, return statements, string concatenation, and array definitions.
Example: Using the Result Directly
<?php
function itemCount(int $count): string
{
return $count . ' ' . ($count === 1 ? 'item' : 'items');
}
echo itemCount(1) . "\n";
echo itemCount(3) . "\n";
$user = ['name' => 'Vimal', 'premium' => true];
$profile = [
'name' => $user['name'],
'badge' => $user['premium'] ? 'Premium member' : 'Free member',
'storageGb' => $user['premium'] ? 100 : 5,
];
print_r($profile);
Output
1 item
3 items
Array
(
[name] => Vimal
[badge] => Premium member
[storageGb] => 100
)
Singular/plural labels, CSS classes, badges, and limits are typical uses: small decisions embedded in a larger expression.
Ternary in HTML Templates
The ternary operator works well inside <?= ?> output tags:
<?php
$tasks = [
['title' => 'Write lesson', 'done' => true],
['title' => 'Record video', 'done' => false],
];
?>
<ul>
<?php foreach ($tasks as $task): ?>
<li class="<?= $task['done'] ? 'done' : 'pending' ?>"><?= htmlspecialchars($task['title']) ?> <?= $task['done'] ? '✔' : '' ?></li>
<?php endforeach; ?>
</ul>
Output (HTML)
<ul>
<li class="done">Write lesson ✔</li>
<li class="pending">Record video </li>
</ul>
The ternary chooses the CSS class and an optional check mark for each task.
Precedence: Use Parentheses
The ternary operator has low precedence — lower than concatenation (.), arithmetic, and comparisons. When it appears inside a larger expression, wrap it in parentheses.
The Concatenation Trap
<?php
$isActive = false;
echo "Status: " . $isActive ? 'Active' : 'Inactive';
echo "\n";
echo "Status: " . ($isActive ? 'Active' : 'Inactive');
echo "\n";
Output
Active
Status: Inactive
Why This Happens
In the first line, . is evaluated first, so PHP reads it as:
("Status: " . $isActive) ? 'Active' : 'Inactive'
"Status: " . false is the string "Status: ", which is truthy, so the result is 'Active' — and the label text is lost entirely. The parentheses in the second line make the ternary a single unit.
Rule: whenever a ternary is part of a larger expression, put it in parentheses.
Nested Ternaries
A ternary can contain another ternary, but since PHP 8.0, nesting without parentheses is a fatal error:
<?php
$score = 75;
// Fatal error in PHP 8:
// echo $score >= 90 ? 'A' : $score >= 75 ? 'B' : 'C';
echo $score >= 90 ? 'A' : ($score >= 75 ? 'B' : 'C');
Output
B
Even with parentheses, nested ternaries quickly become hard to read. For three or more outcomes, use match (true):
<?php
$score = 75;
$grade = match (true) {
$score >= 90 => 'A',
$score >= 75 => 'B',
default => 'C',
};
echo $grade;
Output
B
Each outcome is on its own line, which makes the logic easy to scan and extend. See PHP Match.
The Short Ternary ?: (Elvis Operator)
What It Is
If you leave out the middle part of a ternary, $a ?: $b returns $a when it is truthy, otherwise $b. It is shorthand for $a ? $a : $b, but $a is evaluated only once.
The name "Elvis operator" comes from ?: resembling an emoticon with Elvis Presley's hairstyle.
Example
<?php
$nickname = '';
$title = 'Weekly Report';
$items = [];
echo ($nickname ?: 'Anonymous') . "\n";
echo ($title ?: 'Untitled') . "\n";
echo count($items ?: ['(no items)']) . "\n";
Output
Anonymous
Weekly Report
1
''is falsy, so'Anonymous'is used.'Weekly Report'is truthy, so it is kept.[]is falsy, so the fallback array with one element is used.
?: vs ??
Value of $x | $x ?: 'default' | $x ?? 'default' |
|---|---|---|
null | 'default' | 'default' |
| (undefined) | 'default' plus a warning | 'default' |
'' | 'default' | '' |
0 | 'default' | 0 |
'0' | 'default' | '0' |
'PHP' | 'PHP' | 'PHP' |
- Use
?:when any empty value should be replaced, and the variable is known to exist. - Use
??when only missing ornullvalues should be replaced, and0,'', or'0'are valid.
Combining Both
<?php
$query = ['q' => ' '];
$search = trim($query['q'] ?? '') ?: 'all products';
echo "Showing results for: $search\n";
Output
Showing results for: all products
?? safely handles a missing q parameter, trim() removes the spaces, and ?: replaces the resulting empty string.
One-Line if Without Braces
PHP allows an if with a single statement on one line:
<?php
$debug = true;
if ($debug) echo "Debug mode is on\n";
Output
Debug mode is on
This is valid, but it is easy to break: adding a second statement later does not make it part of the if. Most coding standards (including PER Coding Style) require braces for every control structure. Use the braced form:
if ($debug) {
echo "Debug mode is on\n";
}
When Not to Use the Ternary Operator
For Side Effects Instead of Values
// Legal, but unclear
$isValid ? saveOrder($order) : logError($order);
The ternary operator is designed to produce a value. Using it only to call one of two functions hides control flow inside an expression. Use if...else:
if ($isValid) {
saveOrder($order);
} else {
logError($order);
}
For Long or Complex Conditions
If the condition or the values do not fit comfortably on one line, the ternary saves no effort and costs readability. Use if...else, match, or extract the condition into a well-named variable first.
Practical Example: Formatting an Order Summary
<?php
function orderSummary(array $order): string
{
$itemWord = $order['items'] === 1 ? 'item' : 'items';
$shipping = $order['total'] >= 999 ? 'FREE' : '₹79';
$note = trim($order['note'] ?? '') ?: 'No delivery note';
$priority = $order['express'] ? ' [EXPRESS]' : '';
return sprintf(
"Order #%d%s: %d %s, total ₹%s, shipping %s. Note: %s",
$order['id'],
$priority,
$order['items'],
$itemWord,
number_format($order['total']),
$shipping,
$note
);
}
echo orderSummary(['id' => 501, 'items' => 1, 'total' => 450, 'express' => false]) . "\n";
echo orderSummary(['id' => 502, 'items' => 3, 'total' => 2400, 'express' => true, 'note' => 'Leave at gate']) . "\n";
Output
Order #501: 1 item, total ₹450, shipping ₹79. Note: No delivery note
Order #502 [EXPRESS]: 3 items, total ₹2,400, shipping FREE. Note: Leave at gate
Step-by-Step Explanation
$itemWordchooses the singular or plural word.$shippingchooses a label based on the order total.$notecombines??(the key may be missing) with?:(an empty note should be replaced).$priorityadds a marker only for express orders; an empty string means "add nothing".- Each small decision is stored in a well-named variable, so the final
sprintf()stays simple.
Common Mistakes
Missing Parentheses Inside Expressions
Effect: "Status: " . $x ? 'A' : 'B' loses the label and evaluates the wrong condition.
Fix: "Status: " . ($x ? 'A' : 'B').
Unparenthesized Nested Ternaries
Effect: Fatal error in PHP 8.
Fix: Add parentheses, or better, use match (true) or if...elseif.
Using ?: on Possibly Undefined Values
Effect: "Undefined variable" or "Undefined array key" warnings.
Fix: Use ?? for values that may not exist, or combine: ($x ?? '') ?: 'default'.
Using ?: When 0 Is Valid
Effect: A quantity of 0 is replaced by the default.
Fix: Use ?? or an explicit comparison.
Using the Ternary for Side Effects
Effect: Hidden control flow that is hard to read and debug.
Fix: Use if...else.
Best Practices
- Use the ternary operator for short choices between two values.
- Always wrap a ternary in parentheses when it is part of a larger expression.
- Prefer
match (true)orif...elseiffor three or more outcomes. - Use
??for missing ornullvalues, and?:for empty values that are known to exist. - Always use braces with
if, even for one statement.
Official reference: https://www.php.net/manual/en/language.operators.comparison.php#language.operators.comparison.ternary