0

edit : Quote removed. is not related to the question.

Question

How come does it always (when all are truthy) takes the last value ?

Examples :

f= 1 && 2 && 3 //3

f= 'k' && 'd' && 's' //'s'

p.s. : I've noticed that when investigating the pub/sub using $.callbacks

enter image description here

2
  • 5
    The && operator is supposed to be used with boolean operands. But since javascript allows for writing such weakly typed pornography, the result is, well, surprising :-) Commented Oct 7, 2013 at 8:04
  • This is for the performance of execution as the AND is to return true when all the conditions are correct. It will stop checking when the first one fails because the condition will return false when anyone of it is false. So there is no need of checking the next. Commented Oct 7, 2013 at 8:07

7 Answers 7

6

Operator && acts as an if-statement. The short-circuit occurs only if a value is false. Otherwise, it keeps evaluating statements.

When you write a && b it means: a ? b : a. Similarly, a || b means: a ? a : b.

Sign up to request clarification or add additional context in comments.

2 Comments

looking at your answer more deeply - it actually answer my question. since this acts like a chain. if A then B and (same round) if B then C - which means im left with C.
The || is deeply used to assign default value to a variable, like this: setting = setting || false will assign false if no value are provided by the user (i.e. undefined)
4

Edit: author has clarified the question significantly.

JavaScript logical AND operator return the left operand if it is falsy or else it returns the right operand. Let us take a look at the table of logical truth:

A B A && B true true true true false false false true false false false false 

As you can see, if A is false, we can return it:

A A && B false false false false 

If A is not false, we can return B:

B A && B true true false false 

This is a minor optimization, which leads to interesting sideeffects when used with weak typing, such as inline if:

var result = callback && callback() // Generally equivalent to a simple if: if (callback) result = callback(); else result = null; 

Also using default options:

name = name || 'John'; // Generally equivalent to a simple if: if (!name) name = 'John'; 

As to why it happens, well, because these operators are defined like that in ECMA-262.

2 Comments

the question was about returning the last value
@RoyiNamir, I've now updated the answer.
3

So how come does it always (when all are truthy) takes the last value ?

Because it can't short-circuit if the leading values are truthy, because it's an "AND" operator, and all operands must be truthy to satisfy the condition.


Re your comment below:

yes but why does it returns the last value ?

Because it's useful. :-) In the very first version of JavaScript from Netscape, it just returned true if the overall expression was true and false if not, but almost immediately they realized that it's much more useful if it returns the final operand.

For instance, you can do this:

var value = obj && obj.value; 

...which will set value to be either a falsey value (if obj is falsey) or obj.value (if obj is not falsey). Importantly, it won't throw an error if obj is falsey. Very handy for guarding if you don't know for sure that obj is set. You don't have to stop at one level, either:

var value = obj && obj.sub && obj.sub.value; 

value will either be falsey, or the value of obj.sub.value if both obj and obj.sub are truthy (e.g., because we seem to be using them as objects, they're object instances rather than null or undefined).

|| does the same sort of thing: It returns its first truthy operand.

More: JavaScript's Curiously Powerful OR Operator (||)

4 Comments

yes but why does it returns the last value ?
@RoyiNamir: Sorry, updated. :-)
@T.J.Crowder, your final example with an if statement would work fine if && returned boolean instead of the last operand, actually.
@Denis: Ah, yes, I was grouping the statement incorrectly, thanks.
1

Because if first one is truthy, then it should go on and check second operand till the last one. If you would go with 1 || 2 || 3 instead it will return 1.

2 Comments

this does not explain the act of RETURNNING the last value
1

&& is a logical operator. This tests whether a value is truthy or falsy. This linked article explains that falsy values are equal to undefined, null, NaN, 0, "" and false.

Logical expressions are checked from left to right. If any part of the expression is evaluated t be falsy, the remainder of the expression will not be evaluated. In your examples, the value is always truthy. Here we can break down your first expression:

f = 1 && 2 && 3; f = 1 /* Okay, 1 is a truthy value, lets continue... */ f = 2 /* Still truthy, let's continue... */ f = 3 /* Still truthy, we've reached the end of the expression, f = 3. */ 

If any of the values before 3 were falsy, the expression would have ended. To show this in action, simply redeclare your variable as:

f = 1 && 2 && 0 && 3; 

Here 0 is a falsy value (as mentioned above). The execution of your expression here will end at 0:

f = 1 /* Okay, 1 is a truthy value, lets continue... */ f = 2 /* Still truthy, let's continue... */ f = 0 /* Hey, this is falsy, lets stop here, f = 0. */ f = 3 /* We never get here as the expression has ended */ 

Here f ends up being 0.

In your jQuery.Topic() example, && is used to ensure that id actually exists:

topic = id && topics[id] 

We can break this down in the same way:

/* Assume this is your topics array: */ topics = ["", "My First Topic", "My Second Topic"]; /* If we pass in the value 1 as "jQuery.Topic(1)": */ topic = id && topics[id] topic = 1 /* This is truthy, let's continue... */ topic = topics[1] /* topics[1] === "My First Topic" */ /* Now lets assume we pass in nothing as "jQuery.Topic()": */ topic = id && topics[id] topic = null /* This is falsy, let's stop here, topic = null. */ 

The following if statement will only work if topic is truthy. In the first example, this is the case as topic has a value which is set to a string which isn't empty. In the second example, topic is null which is falsy.

1 Comment

It's an expression, not a statement. And it also does not take multiple operands, it's just multiple && expressions: 1 && (2 && (0 && 3)).
1

The ECMAScript Standard states 12.11.2 Runtime Semantics: Evaluation:

LogicalANDExpression : LogicalANDExpression && BitwiseORExpression 1. Let lref be the result of evaluating LogicalANDExpression. 2. Let lval be GetValue(lref). 3. Let lbool be ToBoolean(lval). 4. ReturnIfAbrupt(lbool). 5. If lbool is false, return lval. 6. Let rref be the result of evaluating BitwiseORExpression. 7. Return GetValue(rref). 

That is, first we check whether the first operand is evaluated to be a "falsy" value (null, false, 0). If it is, then the first operand is returned.

If, however, it's "thruthy", then the same process is repeated for the second operand and if it is evaluated as a truthy value, then the original value is returned (7. Return GetValue(rref)).

Comments

0

Short-circuit evaluation and returning the second expression instead of a bool are quite useful features.

The && operator evaluates the left operand and if it's truthy evaluates the right operand. Similarly the || operator evaluates the left operand and if it's falsy evaluates the right operand.

This allows to write things like

draw_element(color || "#F00"); 

with the meaning of using color unless if it's not specified (e.g. color is null, undefined or "") and in that case the default value is used.

You can even use things like

draw_element(color || pick_new_color()); 

and the function pick_new_color() will be called only if a color is not specified.

A very common use of && instead is to avoid errors, e.g:

if (x && x.constructor == Array) { ... } 

because if x is null or undefined you cannot access attributes (an exception would be raised if you try). The fact that && returns the first result if it's falsy instead of just false is not so useful indeed. Your code example does it, but it's not something you will find often in Javascript programs.

To recap: && and || are short-circuiting (i.e. they don't even evaluate the second operand if the result is known after evaluating the first) and this is very useful. They also return the falsy/truthy value itself instead of a bool, and this is very useful for || (not so much useful for &&).

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.