为什么逻辑运算符(&&和||)总是返回布尔结果呢?

为什么这些逻辑运算符返回一个对象而不是布尔值?

var _ = (obj.fn && obj.fn() ) || obj._ || ( obj._ = {} ); var _ = obj && obj._; 

我想知道为什么它返回的结果obj.fn() (如果它被定义)或obj._但不是布尔结果。

 var _ = ((obj.fn && obj.fn() ) || obj._ || ( obj._ == {/*soemthign*/}))? true: false 

将返回布尔值。

UPDATE

请注意,这是基于我的testing。 我不能完全依靠。

这是一个expression式,不分配true值或false值。 而是分配计算的值。

我们来看看这个expression式。

一个例子expression式:

 var a = 1 || 2; //a = 1 //its because a will take the value (which is not null) from left var a = 0 || 2; //so for this a=2; //its because the closest is 2 (which is not null) var a = 0 || 2 || 1; //here also a = 2; 

你的表情:

 var _ = (obj.fn && obj.fn() ) || obj._ || ( obj._ = {} ); // _ = closest of the expression which is not null //in your case it must be (obj.fn && obj.fn()) //so you are gettig this 

另一个expression:

 var a = 1 && 2; //a = 2 var a = 1 && 2 && 3; //a = 3 //for && operator it will take the fartest value //as long as every expression is true var a = 0 && 2 && 3; //a = 0 

另一个expression:

 var _ = obj && obj._; //_ = obj._ 

在JavaScript中,都是|| 和&&是逻辑短路运算符,当从左到右求值时返回第一个完全确定的“逻辑值”。

在expression式X || Y中,首先计算X,并将其解释为布尔值。 如果这个布尔值是“true”,那么它被返回。 而Y不被评估。 (因为Y是真还是Y是假的,X || Y已经完全确定了。)这就是短路部分。 如果这个布尔值是“false”,那么我们仍然不知道X || Y是真还是假,直到我们评估Y为止,并将其解释为布尔值。 那么Y就会返回。

AND &&也是这样,除非停止评估第一个参数是否为false。

第一个棘手的部分是,当一个expression式被评估为“真”时,expression式本身被返回。 在逻辑expression式中被视为“真”,但您也可以使用它。 所以这就是为什么你看到实际值被返回。

第二个棘手的部分是,当一个expression式被评估为“false”时,那么在JS 1.0和1.1中,系统将返回一个布尔值“false”; 而在JS 1.2中则返回expression式的实际值。

在JS中,null,false,0,“”和undefined都算作false。

[这里当然是为了讨论而引用逻辑值。 当然,string“false”“false”与false的值不同,因此是正确的。 ]

最简单的说法是:

|| 运算符返回第一个真值,如果没有真值,则返回最后一个值(这是一个falsy值)。

&&运算符返回第一个falsy值,如果没有falsy,则返回最后一个值(这是一个真值)。

它真的很简单。 在你的控制台上进行实验,看看你自己。

我想你在这里有基本的JavaScript方法论问题。 现在,JavaScript是一种松散types的语言,因此它处理逻辑操作的方式和方式与其他标准语言(如Java和C ++)不同。 JavaScript使用一种称为“types强制”的概念来确定逻辑操作的值,并始终返回第一个“true”types的值。 例如,看看下面的代码:

 var x = myshit || document; // after execution of the line above, x = document 

这是因为“myshit”是一个先验未定义的实体,在testing时它总是被评估为false,所以JavaScript会跳过这个实体并testing下一个实体是否为“真”值。 由于文档对象是JavaScript已知的,所以它返回一个真正的值,JavaScript返回这个对象。

如果你想要一个布尔值返回给你,你必须把你的逻辑条件语句传递给一个函数,如下所示:

 var condition1 = myshit || document; function returnBool(cond){ if(typeof(cond) != 'boolean'){ //the condition type will return 'object' in this case return new Boolean(cond).valueOf(); }else{ return; } } // Then we test... var condition2 = returnBool(condition1); window.console.log(typeof(condition2)); // outputs 'boolean' 

首先,它必须是真的返回,所以如果你正在testing真实性,那么它没有任何区别

其次,它可以让你按照以下方式进行分配:

 function bar(foo) { foo = foo || "default value"; 

我们可以参考JS的spec(11.11)这里:

语义

生产LogicalANDExpression:LogicalANDExpression && BitwiseORExpression的计算方法如下:

  1. 评估逻辑和expression。

2.调用GetValue(Result(1))。

3.Call ToBoolean(结果(2))。

4.如果结果(3)为假,返回结果(2)。

5.评估BitwiseORExpression。

6.调用GetValue(Result(5))。

7.返回结果(6)。

看这里的规格

比较:

 var prop; if (obj.value) {prop=obj.value;} else prop=0; 

有:

 var prop=obj.value||0; 

返回一个真实的expression式 – 而不仅仅是真或假 – 通常会使您的代码更短,并且仍然可读。 ||这是很常见的,而不是&&。

使用Boolean()函数,如下所示:

 var a = 0 || 1;// a = 1 var a = Boolean(0 || 1);// a = true