5
var p = "null"
var q = null;
(p == q) //false. as Expected.

p.replace(null, "replaced") // outputs replaced. Not expected.
p.replace("null", "replaced") //outputs replaced. Expected.

q.replace(null, "replaced") // error.  Expected.
q.replace("null", "replaced") //error. Expected.

Why? Does replace not differentiate between "null" and null?

I ask because I ran into a bug in angularjs:

replace((pctEncodeSpaces ? null : /%20/g), '+');

If for example, someone had a username of "null" and it was used as url, it would be replaced with "+" on any $http calls. e.g. GET /user/null.

Not that this scenario would occur often, but I'm more curious why replace treats null and "null" as the same thing. Does replace do a .tostring on null before it does the replacement? Is this just a quirk of Javascript?

I verified this on both IE and Chrome's implementations of replace.

3
  • replace is a method of String and, as such, can only be called on strings. Commented Apr 30, 2013 at 15:50
  • Sorry, maybe I should remove the q part. That's not what I'm asking about, I realize I should get that error. Commented Apr 30, 2013 at 15:51
  • @Rastapopulous yes, that would make the question clearer. The q part is just distracting. Commented Apr 30, 2013 at 16:04

4 Answers 4

5

Yes, this is expected according to the spec for replace (bolded relevant line, or page 146 of the ECMA-262 final draft). The first argument is checked to see if it is a regex and if not, it has toString() called on it (well, converted to a string somehow).

15.5.4.11 String.prototype.replace(searchValue, replaceValue)

Let string denote the result of converting the this value to a string.

Cut for brevity

IfsearchValue is not a regular expression, let searchString be ToString(searchValue) and search string for the first occurrence of searchString. Let m be 0.

Cut for brevity

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

8 Comments

please consider removing text to avoid distraction, not adding it!
@Alnitak you mean you don't like walls of text?!
@RussCam yes, there was so much (irrelevant) information in your answer as to render it IMHO useless.
@Alnitak I'm not sure that the specification for how replace() should work is useless, but I agree that it does detract from the main point so will trim it.
I didn't say that the specification is useless, I said that it made your answer useless - fine distinction ... ;-)
|
4

In the ES5 specification for String.prototype.replace:

15.5.4.11 String.prototype.replace (searchValue, replaceValue)

...

If searchValue is not a regular expression, let searchString be ToString(searchValue) and search string for the first occurrence of searchString

So, "".replace(null, XXX) will indeed convert the null to the string "null"

Note that ToString() does not mean null.toString() - it's an internal defined operation within the JavaScript interpreter.

2 Comments

And that is what he expected. The question is around the first line (p.replace(null, "replaced") // outputs replaced. Not expected.).
@alexn that comment relates to my previous answer, which incorrectly focussed on q.
0

For the not expected one, there's a simple answer. The null is casted to string by the replace() method.
So that is also an expected action

Comments

0
"null".replace(null, "replaced") // outputs replaced. Not expected.

Does replace not differentiate between "null" and null

This is because parameter 1 of replace is converted to String.

''+null === "null"; // true by cast to string

Furthermore, as replace takes RegExp objects, you can also think about how

RegExp(null).toString() === "/null/"; // true

4 Comments

the concatenation is irrelevant - there's probably a ToString cast required in the ECMAScript specification.
@Alnitak , null == 'null' and (obviously) null === 'null' are both false.
irrelevant - the real answer is that the .replace method requires that the first parameter use the internal ToString() cast. Please go read the ES5 specs. The null RegExp object is a red-herring too - a null has no type.
by which I mean that null is not an instanceof RegExp, so the implementation of .replace cannot test null for type equality. Strictly speaking typeof null === "object".

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.