第三章:原生类型
在第一和第二章中,我们几次提到了各种内建类型,通常称为“原生类型”,比如 String
和 Number
。现在让我们来仔细检视它们。
这是最常用的原生类型的一览:
String()
Number()
Boolean()
Array()
Object()
Function()
RegExp()
Date()
Error()
Symbol()
—— 在 ES6 中被加入的!
如你所见,这些原生类型实际上是内建函数。
如果你拥有像 Java 语言那样的背景,JavaScript 的 String()
看起来像是你曾经用来创建字符串值的 String(..)
构造器。所以,你很快就会观察到你可以做这样的事情:
var s = new String( "Hello World!" );
console.log( s.toString() ); // "Hello World!"
这些原生类型的每一种确实可以被用作一个原生类型的构造器。但是被构建的东西可能与你想象的不同:
var a = new String( "abc" );
typeof a; // "object" ... 不是 "String"
a instanceof String; // true
Object.prototype.toString.call( a ); // "[object String]"
创建值的构造器形式(new String("abc")
)的结果是一个基本类型值("abc"
)的包装器对象。
重要的是,typeof
显示这些对象不是它们自己的特殊 类型,而是 object
类型的子类型。
这个包装器对象可以被进一步观察,像这样:
console.log( a );
这个语句的输出会根据你使用的浏览器变化,因为对于开发者的查看,开发者控制台可以自由选择它认为合适的方式来序列化对象。
注意: 在写作本书时,最新版的 Chrome 打印出这样的东西:String {0: "a", 1: "b", 2: "c", length: 3, [[PrimitiveValue]]: "abc"}
。但是老版本的 Chrome 曾经只打印出这些:String {0: "a", 1: "b", 2: "c"}
。当前最新版的 Firefox 打印 String ["a","b","c"]
,但它曾经以斜体字打印 "abc"
,点击它可以打开对象查看器。当然,这些结果是总频繁变更的,而且你的体验也许不同。
重点是,new String("abc")
为 "abc"
创建了一个字符串包装器对象,而不仅是基本类型值 "abc"
本身。