In this case (with var a
in scope), both of the two posted pieces of code have identical semantics as x === undefined
is only true when x is undefined and typeof x
will only returned "undefined" when x is undefined (or not resolved in the execution context).
That out of the way, we end up with:
undefined === undefined
vs.
"undefined" === "undefined"
So, even in a naive implementation case the "difference" between the two is SameObject(a,b)
vs StringEquals(a,b)
as per the rules for Strict Equality Comparison.
But modern implementations of JavaScript are quite competitive and, as can be seen, are very well optimized for this case. I don't know of the exact implementation details, but there are at least two different techniques that could allow the performance (in FF/Chrome/Webkit) to be the same for both cases:
ECMAScript implementations may intern strings, such that there is only one "undefined" string. This would make the StringEquals(a,b)
effectively the same as SameObject(a,b)
which would end up amounting to a "pointer comparison" in the implementation - this alone could explain why the performance is the same.
Additionally, because typeof x === "undefined"
is a common idiom, it could be translated during the parsing to end up in a special call that performs the same, say TypeOfUndefined(x)
. That is, the implementation could bypass the ===
(and StringEquals
) entirely if it so chose.
IE comes out as a the "clear loser" and seems to be missing an applicable optimization here.
The implementation of the undefined
value is outside the scope of ECMAScript; there are no mandates that it must be a single value/object in the implementation.
In practice, however, undefined
(and other special values like null
) is most likely implemented as either a singleton (e.g. "one object in memory") or as an immediate value or value flag (such that there is actually no undefined object).