为什么这个三元语句 return 在 shorthand 表示法中误报?

Why does this ternary statement return false positives when in shorthand notation?

我一直在摸不着头脑,因为除了格式之外,这些陈述看起来几乎相同 - 然而 shorthand 似乎评估不同,并通过 returning 产生误报不该为真。

在下面的例子中,假设 programRecord.Award = 'Emmy'targetAward = 'Oscar'

给出误报的错误代码:

private bool MatchMe(string programId, string targetAward, string targetLevel, Program programRecord)
{
    var isMatched = programRecord.Status == "Active"
        && string.IsNullOrEmpty(programId) ? true : programRecord.Pid == programId
        && string.IsNullOrEmpty(targetAward) ? true : programRecord.Award == targetAward
        && string.IsNullOrEmpty(targetLevel) ? true : programRecord.Level == targetLevel;
    return isMatched;
}

好的代码:

    private bool MatchMe(string programId, string targetAward, string targetLevel, Program programRecord)
    {
        var isMatched = programRecord.Status == "Active";
        var isMatched2 = string.IsNullOrEmpty(programId) ? true : programRecord.Pid == programId;
        var isMatched3 = string.IsNullOrEmpty(targetAward) ? true : programRecord.Award == targetAward;
        var isMatched4 = string.IsNullOrEmpty(targetLevel) ? true : programRecord.Level == targetLevel;
        var doIMatch = isMatched && isMatched2 && isMatched3 && isMatched4;
        return doIMatch;
    }

导致此问题的 shorthand 版本中发生了什么?我认为一个 false 值会强制整个语句为 return false,但是缩写版本不会发生这种情况。

你比较的格式不对。如果要正确解释,您实际上需要括号来强制内联。

你应该有以下内容

private bool MatchMe(string programId, string targetAward, string targetLevel, Program programRecord)
{
    var isMatched = programRecord.Status == "Active"
        && (string.IsNullOrEmpty(programId) ? true : programRecord.Pid == programId)
        && (string.IsNullOrEmpty(targetAward) ? true : programRecord.Award == targetAward)
        && (string.IsNullOrEmpty(targetLevel) ? true : programRecord.Level == targetLevel);
    return isMatched;
}

三元运算符没有像您想象的那样被计算。考虑以下示例:

var val = true ? true : false && false ? false : false;
var val2 = (true ? true : false) && (false ? false : false);
Console.WriteLine(val);
Console.WriteLine(val2);

输出:

True
False

所以你看,第一个表达式被计算为

var val = true ? true : (false && false ? false : false);

如其他人所示,您需要将三元表达式括在方括号中。原因是,&& 运算符的优先级高于 ?: 运算符。

参见:7.2.1 Operator precedence and associativity