PHP为什么会给出意外的输出?

3
$i = 2;
$result = ($i == 2) ? "Two" : ($i == 1) ? "One" : "Other";

echo $result; // outputs: One

当使用C#编写相同的代码时,输出结果为:Two

int i=2;
String result = (i == 2) ? "Two" : (i == 1) ? "One" : "Other" ;
Console.Write( result ); // outputs: Two

3
这并不是出乎意料的,只是不符合直觉。这正是文档建议不要嵌套三元运算符的原因:“注意:建议避免“嵌套”三元表达式。当在一个语句中使用多个三元运算符时,PHP的行为是不明显的。” - Mark Baker
1
你对编译器没有感情。嵌套三元运算符... - Answers_Seeker
3个回答

5
三元运算符是从左到右进行求值的。
($i == 2) ? "Two" : ($i == 1) ? "One" : "Other"
"Two" ? "One" : "Other"  // first part evaluated to "Two"
"One"                    // non-empty strings evaluate to true

所以你的输出应该是One,而不是Other。这有点棘手。
来自手册的明智之言:
建议避免“堆叠”三元表达式。在单个语句中使用多个三元运算符时,PHP的行为是不明显的。

2

@light已经给出了解释,但为了得到您想要的结果,您需要添加额外的大括号:

$i = 3;
$result = ($i == 2) ? "Two" : (($i == 1) ? "One" : "Other");
echo $result, PHP_EOL;

$i = 2;
$result = ($i == 2) ? "Two" : (($i == 1) ? "One" : "Other");
echo $result, PHP_EOL;

$i = 1;
$result = ($i == 2) ? "Two" : (($i == 1) ? "One" : "Other");
echo $result, PHP_EOL;

Demo


0

这是因为C#是强类型的,需要一个布尔值作为三元运算符的第一个参数,而PHP是弱类型的,基本上任何值都可以转换为它的布尔等价物。此外,三元运算符是从左到右进行评估的。这意味着什么?

在C#中,我们需要在运算符的最左边使用布尔值,所以这个表达式:

String result = (i == 2) ? "Two" : (i == 1) ? "One" : "Other" ;

将按照以下顺序进行评估:

String result = (i == 2) ? "Two" : ((i == 1) ? "One" : "Other");

i==2 等于 true,因此 "Two" 将被分配为最终结果。在 PHP 中,它看起来有点不同。我们可以解释这个表达式:

$result = ($i == 2) ? "Two" : ($i == 1) ? "One" : "Other";

像这样

$result = (($i == 2) ? "Two" : ($i == 1)) ? "One" : "Other";

$i 等于 2,所以第一个表达式的结果是 "Two"。非空字符串值在 PHP 中等于 true,所以最终结果是 "One"。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接