diff --git a/src/ExpressionParser.php b/src/ExpressionParser.php index eb33868918f..13e0f0876ed 100644 --- a/src/ExpressionParser.php +++ b/src/ExpressionParser.php @@ -183,11 +183,14 @@ private function parseConditionalExpression($expr): AbstractExpression if (!$this->parser->getStream()->nextIf(/* Token::PUNCTUATION_TYPE */ 9, ':')) { $expr2 = $this->parseExpression(); if ($this->parser->getStream()->nextIf(/* Token::PUNCTUATION_TYPE */ 9, ':')) { + // Ternary operator (expr ? expr2 : expr3) $expr3 = $this->parseExpression(); } else { + // Ternary without else (expr ? expr2) $expr3 = new ConstantExpression('', $this->parser->getCurrentToken()->getLine()); } } else { + // Ternary without then (expr ?: expr3) $expr2 = $expr; $expr3 = $this->parseExpression(); } diff --git a/src/Node/Expression/ConditionalExpression.php b/src/Node/Expression/ConditionalExpression.php index 2c7bd0a276c..d7db993579c 100644 --- a/src/Node/Expression/ConditionalExpression.php +++ b/src/Node/Expression/ConditionalExpression.php @@ -23,14 +23,23 @@ public function __construct(AbstractExpression $expr1, AbstractExpression $expr2 public function compile(Compiler $compiler): void { - $compiler - ->raw('((') - ->subcompile($this->getNode('expr1')) - ->raw(') ? (') - ->subcompile($this->getNode('expr2')) - ->raw(') : (') - ->subcompile($this->getNode('expr3')) - ->raw('))') - ; + // Ternary with no then uses Elvis operator + if ($this->getNode('expr1') === $this->getNode('expr2')) { + $compiler + ->raw('((') + ->subcompile($this->getNode('expr1')) + ->raw(') ?: (') + ->subcompile($this->getNode('expr3')) + ->raw('))'); + } else { + $compiler + ->raw('((') + ->subcompile($this->getNode('expr1')) + ->raw(') ? (') + ->subcompile($this->getNode('expr2')) + ->raw(') : (') + ->subcompile($this->getNode('expr3')) + ->raw('))'); + } } }