为什么!! 1 ==“1”等于true,!! 2 ==“2”等于false?

正如标题所述,为什么:

> !!1=="1" 

等于

 True 

 > !!2=="2" 

等于:

 False 

同样,为什么> "1"==true等于true> "2"==true等于false

我很困惑。 这些只是在JS错误或这是怎么回事?

根据运算符优先级规则,逻辑! 具有比==更高的优先级。 所以,在这两种情况下!! 首先评估。

注意: 这个答案已经解释了各种物体的真实性。

第一种情况

 !!1 == "1" 

!1将被评估为false ,因为1被认为是Truthy。 否定我们变得true 。 所以expression就变成了

 true == "1" 

现在,强制规则就像你使用==运算符一样,按照ECMAScript 5.1规范中定义的抽象相等性比较algorithm进行评估,

6.如果Type(x)Boolean ,则返回比较结果ToNumber(x) == y

所以, true将被转换为一个数字, 对于布尔值 ,按照ToNumberalgorithm是1。 现在expression成为

 1 == "1" 

现在,

4.如果Type(x)NumberType(y)String ,则返回比较结果x == ToNumber(y)

所以,按照ToNumberalgorithm , "1"将被转换为一个数字,并且将给出1。 这就是为什么它在第一种情况下是true的。

第二种情况

这里适用相同的规则。

 !!2 == "2" 

 true == "2" 

然后

 1 == "2" 

成为

 1 == 2 

这是不true ,这就是为什么第二个案件打印false

tldr; 这是由于==运算符algorithm中的[ToNumber]转换引起的。

第一步是简化expression式。 由于!!x=="x"被parsing为(!!x)=="x"!!a_truthy_expression -> true ,所以相等的实际相关expression式是

 !!1=="2" -> true=="1" -> Boolean==String !!2=="2" -> true=="2" -> Boolean==String 

那么再看看11.9.3的抽象平等比较algorithm的规则,并跟随应用程序产出

规则6 – 如果Type(x)是布尔型,则返回比较结果ToNumber(x)== y。

其结果分别是Number==String或1 ==“1”和1 ==“2” 1 。 然后是规则

规则7 – 如果Type(x)是Number和Type(y)是String,则返回比较结果x == ToNumber(y)。

应用的结果分别是Number==Number或1 == 1和1 == 2; 后者显然是错误的。

规则1 – 如果types(x)与types(y)相同,则[由c.iii。]如果x与y的数值相同,则返回true [否则返回false]。

(当应用补充规则时,相同的algorithm解释了String==Boolean情况。)


1要查看应用的[ToNumber]规则,请考虑:

 +false -> 0 +true -> 1 +"1" -> 1 +"2" -> 2 

它是一个优先运算符问题。

! 运算符是一个一元运算符。 这意味着左侧必须是expression式或布尔可评估部分。 请参阅Javascript MDN 。

 !!1==1 is not necessary !!(1==1) !!2==2 is not necessary !!(2==2) 

我认为这些expression式应该是一致的,如果相等的运算符有更多的优先权! 运营商。 但是,如果我们考虑相反的话,那么评估第一个否定就是:

 !!1 == 1 !1 -> false !!1 -> true !!1 == 1 

和这两个

 !!2==2 !2 -> false !!2 -> true (!!2) == 2 -> false 

那是因为! 运算符优先于==运算符

请参阅Mozilla运算符首选项

!!1等于真,“1”等于真(“0”是假,所以是每隔一个string)。 所以!!1 == "1"计算结果为true == true ,这当然返回true。

!!2也等于真。 正如我前面提到的,“2”不是“1”,所以是错误的。 因此,我们有true == false ,这当然返回false。

如果你想看看2(一个数字)是否等于“2”(一个数字的string表示),那么你所要做的就是2 == "2" ,它的计算结果是2 == 2 ,这就是真正。 不同的是,我们没有比较布尔值和布尔值。 我们正在比较一个数字和一个数字。

基本上,把!! 在一个数字前面转换为一个布尔值,强制JavaScript将您的string转换为布尔值而不是数字。

因为当您进行平等检查时,“1”可能被视为“真实”,而不是“身份”,但“2” – 不能。