Этот только что нанес мне сильный удар. Я не знаю, так ли это со всеми браузерами (у меня нет другого компетентного браузера для тестирования), но по крайней мере Firefox имеет два типа строковых объектов.
Откройте консоль Firebugs и попробуйте следующее:
>>> "a"
"a"
>>> new String("a")
String { 0="a"}
Как вы можете видеть визуально, Firefox по-разному относится к new String("a")
и "a"
. В противном случае, однако, оба вида строк ведут себя одинаково. Например, есть доказательства того, что оба используют один и тот же объект-прототип:
>>> String.prototype.log = function() { console.log("Logged string: " + this); }
function()
>>> "hello world".log()
Logged string: hello world
>>> new String("hello world").log()
Logged string: hello world
Так что, очевидно, оба одинаковы. То есть, пока вы не спросите тип.
>>> typeof("a")
"string"
>>> typeof(new String("a"))
"object"
Мы также можем заметить, что когда this
является строкой, это всегда форма объекта:
>>> var identity = function() { return this }
>>> identity.call("a")
String { 0="a"}
>>> identity.call(new String("a"))
String { 0="a"}
Продвинувшись немного дальше, мы видим, что не-строковое представление не поддерживает никаких дополнительных свойств, но строка объекта поддерживает:
>>> var a = "a"
>>> var b = new String("b")
>>> a.bar = 4
4
>>> b.bar = 4
4
>>> a.bar
undefined
>>> b.bar
4
Кроме того, забавный факт! Вы можете превратить строковый объект в необъектную строку, используя функцию toString()
:
>>> new String("foo").toString()
"foo"
Никогда не думал, что будет полезно позвонить String.toString()
! В любом случае.
Итак, во всех этих экспериментах возникает вопрос: почему в JavaScript есть два типа строк?
Комментарии показывают, что это также относится к каждому примитивному типу JavaScript (включая числа и bool).