January 09, 2020
4 min read ☕️

Click now Keep reading to see the beginner's guide to what computedValue && "One Truthy Boi" evaluates to!
To truthy, or not to truthy?
Let's do a little code experiment.
How does the value of computedValue affect what the expression computedValue && "One Truthy Boi" evaluates to?
Well, let's take a gander in ${insertYourFavoriteJavascriptConsole} (I'll run mine in the Chrome browser console).
When computedValue is truthy:
let computedValue = true;
let result = computedValue && 'One Truthy Boi';
console.log(result); // "One Truthy Boi"Versus when computedValue is falsey:
let computedValue = false;
let result = computedValue && 'One Truthy Boi';
console.log(result); // falseAnd to prove it, a screenshot of it running:

Strange.
So, result will either be false or "One Truthy Boi" depending on what the left-hand-side of the && boolean operation evaluates to.
Interesting... 🤔
Why this is weird to me
It turns out this is a pretty standard feature in dynamic languages like JavaScript, Ruby, and Python. However, if you're coming from the land of types, this is... odd. To understand why let's take a look at a little history...
Normally, when performing (left expression && right expression), you're checking for a true or false evaluation, like in a conditional expression for an if/else block.
This is called a boolean expression and evaluates to either true OR false (two values only; one or the other, not both).
In the ancient manuscripts C language, boolean primitives weren't a thing until C99.
By that I mean you couldn't assign a type of bool_t to a variable before C99.
Before the boolean types were added, other things acted as true and false.
Instead, boolean operations were done on integers, where 0 is false and any other number is true.
Similarly, in dynamically-typed languages, many things can act as true and false, even though they aren't literally true or false primitive values.
The expression true && "not a boolean" works in dynamically-typed languages because true is, well, true and "not a boolean" is truthy.
And by truthy, I mean that it ain't an empty string ""!
A few more examples of...
Truthy things:
- non-empty arrays (in JavaScript)
- non-empty strings (in JavaScript)
- anything non-
nilin Ruby, including 0! 😳
Falsey things:
- Empty strings (in JavaScript)
- Empty arrays (in JavaScript)
nil,null,undefined
But here's the kicker: in C, boolean expressions are just that: boolean, one of two values.

In other words:
if (boolean_expression) {
// run this code if boolean_expression == TRUE
} else {
// run this code if boolean_expression == FALSE
}But, the astute reader will notice that, for the typical dynamically-typed language, our boolean expressions evaluate to... anything! (Kind of...)
What's going on here?
Let's look at a quick example:
const leftHandSide = 'some value here';
const rightHandSide = 'One Truthy Boi';
const result = leftHandSide && rightHandSide;
// result = "One Truthy Boi"In this case, the dynamically-typed runtime is coercing the left-hand side of the boolean expression into a boolean value, like:
const leftHandSide = 'some value here';
const rightHandSide = 'One Truthy Boi';
if (Boolean(leftHandSide) === true) {
return rightHandSide;
} else {
return false;
}This is mostly true, but we'll clarify how it actually works next.
The main thing to take away is that if the leftHandSide expression evaluates to false, then a falsey value is returned.
Let's take a deeper look.
So far, we've only looked at && (AND), but there's also || (OR) and ! (NOT).
According to MDN on logical operators, each of these behaves like the following:
- Logical AND:
expr1 && expr2- If
expr1can be converted totrue, returnsexpr2; else, returnsexpr1
- If
- Logical OR:
expr1 || expr2- If
expr1can be converted totrue, returnsexpr1; else, returnsexpr2
- If
- Logical NOT:
!expr- Returns
falseif it can be converted totrue; else, returnstrue
- Returns
Take my word for it, but Ruby boolean expression behave pretty much identically.
So, did you catch it?
There's a big difference in what I, coming from a strongly typed background, would expect versus what the actual boolean operation defines:
In the case where the expression short-circuit evaluates, instead of returning a boolean literal (i.e.
trueorfalse), it returns the value that forced the short-circuit path, e.g.undefined && truereturnsundefinedinstead offalse
This is why in the original example we saw computedValue && "One Truthy Boi" return either false or "One Truthy Boi".
This is also why, in React, you can short circuit return jsx like:
function Example() {
const [showGreeting, setShowGreeting] = React.useState(false);
return (
<div>
<button type="button" onClick={() => setShowGreeting(!showGreeting)}>
{showGreeting ? 'Hide greeting' : 'Show greeting'}
</button>
{showGreeting && <p>Hello there! 👋</p>}
</div>
);
}Conclusion
There's an immense amount of flexibility gained from operating as dynamically-typed languages do. Often though, it can produce surprising results if you're not careful. Usually, it works out well, but there are cases where short-circuit evaluation of boolean expressions (logical operators) can produce unexpected results.
I'll leave you with an example.
Take for instance the following React code.
What do you think happens when list.length === 0?
Have a look for yourself below 👀:
function Example() {
const [list, setList] = React.useState([]);
function addItem() {
setList(list.concat(list.length + 1));
}
function clearList() {
setList([]);
}
return (
<div>
<p>List length: {list.length}</p>
<button type="button" onClick={addItem}>
Add One
</button>
<button type="button" onClick={clearList}>
Clear List
</button>
{list.length && (
<ul>
{list.map((item) => (
<li key={item}>{item}</li>
))}
</ul>
)}
</div>
);
}List length: 0
0