views:

4246

answers:

26

I'm using JSLint to go through some horrific JavaScript at work and it's returning a huge number of suggestions to replace == with === when doing things like comparing 'idSele_UNVEHtype.value.length == 0' inside of an if statement.

I'm basically wondering if there is a performance benefit to replacing == with ===. Any performance improvement would probably be welcomed as there are hundreds (if not thousands) of these comparison operators being used throughout the file.

I tried searching for relevant information to this question, but trying to search for something like '=== vs ==' doesn't seem to work so well with search engines...

+122  A: 

The identity (===) operator behaves identically to the equality (==) operator except no type conversion is done, and the types must be the same to be considered equal.

Reference: Javascript Tutorial: Comparison Operators

The == operator will compare for equality after doing any necessary type conversions. The === operator will not do the conversion, so if two values are not the same type === will simply return false. It's this case where === will be faster, and may return a different result than ==. In all other cases performance will be the same.

To quote Douglas Crockford's excellent JavaScript: The Good Parts,

JavaScript has two sets of equality operators: === and !==, and their evil twins == and !=. The good ones work the way you would expect. If the two operands are of the same type and have the same value, then === produces true and !== produces false. The evil twins do the right thing when the operands are of the same type, but if they are of different types, they attempt to coerce the values. the rules by which they do that are complicated and unmemorable. These are some of the interesting cases:

'' == '0'           // false
0 == ''             // true
0 == '0'            // true

false == 'false'    // false
false == '0'        // true

false == undefined  // false
false == null       // false
null == undefined   // true

' \t\r\n ' == 0     // true

The lack of transitivity is alarming. My advice is to never use the evil twins. Instead, always use === and !==. All of the comparisons just shown produce false with the === operator.


Update:

A good point was brought up by @Casebash in the comments and in @Phillipe Laybaert's answer concerning reference types. For reference types == and === act consistently with one another (except in a special case).

var a = [1,2,3];
var b = [1,2,3];

var c = { x: 1, y: 2 };
var d = { x: 1, y: 2 };

var e = "text";
var f = "te" + "xt";

a == b            // false
a === b           // false

c == d            // false
c === d           // false

e == f            // true
e === f           // true

The special case is when you compare a string literal with a string object created with the String constructor.

"abc" == new String("abc")    // true
"abc" === new String("abc")   // false

Here the == operator is checking the values of the two objects and returning true, but the === is seeing that they're not the same type and returning false. Which one is correct? That really depends on what you're trying to compare. My advice is to bypass the question entirely and just don't use the String constructor to create string objects.

Bill the Lizard
So assuming types are the same - is === actually faster? :)
ionut bizau
=== is not quicker if the types are the same. If types are not the same, === will be quicker because it won't try to do the conversion.
Bill the Lizard
But presumably it's never slower, right?
Ray Hidayat
=== will never be slower than ==. They both do type checking, so === doesn't do anything extra compared to ==, but the type check may allow === to exit sooner when types are not the same.
Bill the Lizard
Very nice answer Bill. I love the "evil twins" bit :)
DoctaJonez
is crockford on SO yet?
Allen
@Allen: I hope not. I want him to be writing another excellent book. :)
Bill the Lizard
Just ripped you off (hope that you don't mind too much) http://stackoverflow.com/questions/1525670/javascript-vs/1525693#1525693
voyager
@voyager: Not at all, considering my answer is mostly ripped off from two other sources (cited). :)
Bill the Lizard
Replacing all ==/!= with ===/!== increases the size of the js file, it will take then more time to load. :)
Marco Demajo
Should we really never use `==`? Have you seen [this response](http://stackoverflow.com/questions/359494/javascript-vs-does-it-matter-which-equal-operator-i-use/957602#957602)
Casebash
@Casebash: Yes, I've seen that. That answer doesn't really compare `==` and `===`, which is what this question is about. For every test I've run using reference types `==` and `===` act **consistently** with one another except for one. That's the case pointed out in the comments where `new String("abc") == "abc"` returns `true`, but `new String("abc") === "abc"` returns `false`. My advice in light of this is to *not* use the `String` constructor, and always use `===`.
Bill the Lizard
@Bill The update is technically the 'right' answer. === is reference equality, == is value equality.
Evan Plaice
+60  A: 

Using the == operator (Equality)

true == 1; //true, because 'true' is converted to 1 and then compared
"2" == 2 //true, because 2 is converted to "2" and then compared

Using the === operator (Identity)

true === 1 //false
"2" === 2 // false

This is because the equality operator == does type coercion...meaning that the compiler implicitly tries to convert the values and then does the comparing.

On the other hand, the identity operator === does not do type coercion, and so thus it does not convert the values of the values when comparing

Andreas Grech
I really like the phrase 'type coercion'
Ciaran McNulty
I agree with Ciaran, since I am a spelling, grammar and general all-around semantics Nazi - "conversion" is not the same as "coercion" and the latter is more appropriate; "conversion" implies to me that it will succeed, where as "coercion" allows for failure, which JavaScript does in some instances.
Jason Bunting
This is better than the chosen answer, although I suppose it is less direct.
TM
Better, and yet still incorrect. === is true only when the two values are exactly*the*same*object*.
Software Monkey
@Software Monkey: not for value types (number, boolean, ...)
Philippe Leybaert
A: 

So...Would I be correct in assuming that if no type conversion takes place, there would be a small (probably extremely small) performance gain over ==?

bcasp
But normally you would want to match using the types as well...you want to make sure that the values are Identical...therefore, using === is a better practice.
Andreas Grech
Yes, but you're right on both counts. The performance gain is extremely small.
Bill the Lizard
+1  A: 

There is unlikely to be any performance difference between the two operations in your usage. There is no type-conversion to be done because both parameters are already the same type. Both operations will have a type comparison followed by a value comparison.

Sean
+2  A: 

The === operator is called a strict comparison operator, it does differ from the == operator.

Lets take 2 vars a and b.

For "a == b" to evaluate to true a and b need to be the same value.

In the case of "a === b" a and b must be the same value and also the same type for it to evaluate to true.

Take the following example:

var a = 1;
var b = "1";

if(a == b) //evaluates to true as a and b are both 1
{
    document.write("a == b");
}
if(a === b) //evaluates to false as a is not the same type as b
{
    document.write("a === b");
}

The === operator does not exist in strongly typed languages because it is not needed, but for weakly typed languages like Javascript it makes more sense.

In summary: Using the == operator might evaluate to true in situations where you do not want it to, so using the === operator would be safer. In the 90% usage scenario it won't matter which one you use, but it is handy to know the difference when you get some unexpected behaviour one day.

DoctaJonez
A: 

In a typical script there will be no performance difference. More important may be the fact that thousand "===" is 1KB heavier than thousand "==" :) Javascript profilers can tell you if there is performance difference in your case.

But personally i would do what JSLint suggests. This recommendation is there not because of performance issues, but because type coercion means ('\t\r\n' == 0) is true.

Constantin
Not always true. With gzip compression, the difference would be almost negligible.
Daniel X Moore
Daniel, i could argue that it's still more code to parse, but, well, i don't mean it as a real argument. I actually believe the difference is negligible even without compression.
Constantin
A: 

I cover the differences in a post on my blog recently - http://www.aaron-powell.com/blog.aspx?id=1261

Short story, == is equality comparision without type checking and === is equality comparision with type checking

Slace
@Slace: Your link is broken
Casebash
+6  A: 

I tested this in Firefox with Firebug using code like this:

console.time("testEquality");
var n = 0;
while(true) {
    n++;
    if(n==100000) break;
}
console.timeEnd("testEquality");

and

console.time("testTypeEquality");
var n = 0;
while(true) {
    n++;
    if(n===100000) break;
}
console.timeEnd("testTypeEquality");

My results (tested 5 times each and averaged):

==: 115.2
===: 114.4

so I'd say that the miniscule difference (this is over 100000 iterations, remember) is negligible. Performance ISN'T a reason to do ===. Type safety (well as safe as you're gonna get in JS), and code quality is.

Simon Scarfe
A: 

The problem is that you might easily get into trouble since JS have a lot of implicit conversions meaning ...

var x = 0;
var isTrue = x == null;
var isFalse = x === null;

Which pretty soon becomes a problem. The best sample of why implicit conversion is "evil" can be taken from this code in MFC / C++ which actually will compile due to an implicit conversion from CString to HANDLE which is a pointer typedef type...

CString x;
delete x;

Which obviously during runtime does very undefined things...

Google for impliciti conversions in C++ and STL to get some of the arguments against it...

Thomas Hansen
+14  A: 
Philippe Leybaert
activa: I would clarify, that the strings are so equal only when they are literals. new String("abc") === "abc" is false (according to my research).
Software Monkey
A: 

Here's a chart of how some "falsy" values compare.

Nosredna
+10  A: 
nalply
A: 

In PHP, it is the identical comparison operator, which checks if the value and the type are equal.

Anthony Forloney
+7  A: 

it checked for the same type also for both sides.

var x = '1';
var y = 1;
x === y // false

'string' != 'number' for example

vsync
+2  A: 

It's a comparison operator that also checks type of values. See language operators comparison

Piotr Pankowski
+5  A: 

In Javascript it means of the same value and type

for example

4 == "4" will return true

but

4 === "4" will return false 
Dimitar
wow never new that.
Preet Sangha
+27  A: 

In PHP and JavaScript, it is a strict equality operator. Which means, it will compare both type and values.

Shiki
+1 because your answer addressed both Javascript and PHP, and actually named the operator.
MJB
Additionally if you are comparing objects of the same class, many languages will compare their property/value pairs with ==, whereas === will only evaluate to true if they share the same place in memory.In other words, if you're comparing instance A to instance A, both == and === will evaluate true. But, if you're comparing instance A to instance B (which is a clone of A), == will evaluate true while === will evaluate false.
David
@David: correct. That's why this answer is inaccurate (or even wrong)
Philippe Leybaert
+1  A: 

From the docs:

$a === $b .TRUE if $a is equal to $b, and they are of the same type. (introduced in PHP 4)

klausbyskov
A: 

This link explains it:

http://javascript.about.com/library/blequals.htm

Longball27
+3  A: 

It means equality without type coersion

0==false   // true
0===false  // false, different types
Pop Catalin
AKA, "strict equality"
T.J. Crowder
A: 

From the core javascript reference === Returns true if the operands are strictly equal (see above) with no type conversion.

Paul Butcher
A: 

Take a look :

http://php.net/manual/en/language.operators.comparison.php

Santana
+1  A: 

in PHP it means "Identical" - two variables are identical if the have a) the same value and b) the same type

So: (1 == true) is true, but (1 === true) is false, because they are of different types.

For more info see: http://www.php.net/manual/en/language.operators.comparison.php

ts
A: 

it checks the values well as type of the variable to for equality

Niraj CHoubey
+3  A: 

It's a strict check test.

It's a good thing especially if you're checking between 0 and false and null.

For example, if you have:

$a = 0;

Then:

$a==0; 
$a==NULL;
$a==false;

All returns true and you may not want this. Let's suppose you have a function that can return the 0th index of an array or false on failure. If you check with "==" false, you can get a confusing result.

So with the same thing as above, but a strict test:

$a = 0;

$a===0; // returns true
$a===NULL; // returns false
$a===false; // returns false
Daniel