39

Given the following code:

if ("string") {
    console.log('true!');
}
//logs "true" to the console
if ("string"==true) {
    console.log('true!');
}
//doesn't log anything

Why does this happen? I thought "string" was being cast to a number, as is the boolean. So true becomes 1, and "string" becomes NaN. The second if statement makes sense, but I don't see why the first statement causes the inner loop to be evaluated. What's going on here?

8 Answers 8

64

It is being cast to Boolean. Any non-empty string evaluates to true.

From the ECMAScript Language Specification:

12.5 The if statement

Semantics

The production IfStatement: if ( Expression ) Statement else Statement is evaluated as follows:

  1. Let exprRef be the result of evaluating Expression.
  2. If ToBoolean(GetValue(exprRef)) is true, then
    • Return the result of evaluating the first Statement.
  3. Else,
    • Return the result of evaluating the second Statement.

9.2 ToBoolean

The abstract operation ToBoolean converts its argument to a value of type Boolean according to Table 11:

Table 11 - ToBoolean Conversions

Undefined: false
Null: false
Boolean: The result equals the input argument (no conversion).
Number: The result is false if the argument is +0, -0, or NaN; otherwise the result is true.
String: The result is false if the argument is the empty String (its length is zero); otherwise the result is true.
Object: true


As far as the == operator is concerned, it's complicated, but the gist of it is that if you compare a number to a non-number the latter is converted into a number. If you compare a boolean against a non-boolean, the boolean is first converted to a number, and then the previous sentence applies.

See section 11.9.3 for details.

// Call this x == y.
if ("string" == true) 

// Rule 6: If Type(y) is Boolean,
//         return the result of the comparison x == ToNumber(y).
if ("string" == Number(true))

// Rule 5: If Type(x) is String and Type(y) is Number,
//         return the result of the comparison ToNumber(x) == y.  
if (Number("string") == Number(true))

// The above is equivalent to:
if (NaN == 1)

// And NaN compared to *anything* is false, so the end result is:
if (false)
Sign up to request clarification or add additional context in comments.

2 Comments

Touché. +1 for finding the exact case.
Does the toNumber method only apply for == then?
8

Non-empty strings are truthy, but are not necessarily equivalent to true.


== is a "soft" equality operator.
It uses type coercion to compare two equivalent objects as equal.

All of the following are true:

42 == "42"
0 == false
0 == ""
[] == ""
{} == "[object Object]"
"1" == true

Aribtrary strings are not equivlant to any primitive values. However


When you write if (something), the if will execute if something is "truthy".

All values are truthful except the following:

  • false
  • 0
  • NaN
  • ""
  • null
  • undefined

Comments

1
if ("string"===true)

Should be written this way.

Comments

0

"string" is a string which is not null. In JavaScript everything not being null evaluates "true". So: if("string") is the same as if("string" != null) but "string" is not true, it is still a string value.

Comments

0

I think this is happening because in the first example, your "string" is a non-null object, which translates to true in this context, whereas in the second example, you're asking if this String object is the same as the Boolean object, which it's not, so it translates to false.

Comments

0
if ("string") {
    console.log('true!');
}

As you may already know, if evaluates a boolean expression. So it checks

if((Boolean)"string")

Since (bool)string is true it passes. But in the case of

if ("string"==true) {
    console.log('true!');
}

You are trying to equate a string with a bool, which obviously compares them and returns false.

Comments

0

Simple:

if("string") is evaluated as a boolean. Any value that isn't false is true, no conversion to number or anything of that sort.

Comparing "string" to a boolean value true will obviously yield false.

Comments

0

From the ECMA 262 reference, if you convert implicitly a String to Boolean, and the String is other than the empty String, it will evaluate to true.

Check here

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.