每一种编程语言都有数据结构,但他们各有不同之处。JavaScript 是一种动态语言,变量的类型不用提前声明,你可以使用同一个变量来保存不同的数据类型。
这就和Python的写法差不多:
数据类型
ECMAScript 标準明确定义了7种数据类型:6种原始类型 (Primitive value) 和Object。
原始数据类型:
- Undefined
- Null
- Boolean
- Number
- String
- Symbol (ECMAScript 2015)
判断方法
我们可以透过使用typeof
和Object.prototype.toString()
来判断数据类型。
typeof
在一开始设计 JavaScript 时,数值是由一个标签以及实际数据值表示的。对于基本类型,标签是1;而对于对象类型,标签是0。由于null代表的是空指针(里面都是0),null的类型标签会是0。因此typeof null
就会返回”object”;
|
|
我们可以看一下ECMAScript是怎样定义typeof的:
- Let val be the result of evaluating UnaryExpression.
- If Type(val) is Reference, then
a. If IsUnresolvableReference(val) is true, return “undefined”. - Set val to ? GetValue(val).
- Return a String according to Table 35.
Table 35: typeof Operator Results
Typeof val | 结果 |
---|---|
Item One | Item Two |
Type of val | Result |
Undefined | “undefined” |
Null | “object” |
Boolean | “boolean” |
Number | “number” |
String | “string” |
Symbol | “symbol” |
Object (ordinary and does not implement [[Call]]) | “object” |
Object (standard exotic and does not implement [[Call]]) | “object” |
Object (implements [[Call]]) | “function” |
Object (non-standard exotic and does not implement [[Call]]) | Implementation-defined. Must not be “undefined”, “boolean”, “function”, “number”, “symbol”, or “string”. |
另外,如果直接用typeof
来判断 NaN 的话,它会返回"number"
,对于 NaN 我们可以用isNaN
方法来判断是否一个数字。
Object.prototype.toString()
我们可以利用Object.prototype.toString.call()
或者Object.prototype.toString.apply()
这两个方法判断 Object 的类型,以及 null:
ECMAScript 19.1.3.6 明确定义 Object.prototype.toString():
- If the
this
value isundefined
, return"[object Undefined]"
. - If the
this
value isnull
, return"[object Null]"
. - Let
O
be ! ToObject(this
value). - Let
isArray
be ? IsArray(O
). - If
isArray
istrue
, letbuiltinTag
be"Array"
. - Else if
O
is a String exotic object, letbuiltinTag
be"String"
. - Else if
O
has a [[ParameterMap]] internal slot, letbuiltinTag
be"Arguments"
. - Else if
O
has a [[Call]] internal method, letbuiltinTag
be"Function"
. - Else if
O
has an [[ErrorData]] internal slot, letbuiltinTag
be"Error"
. - Else if
O
has a [[BooleanData]] internal slot, letbuiltinTag
be"Boolean"
. - Else if
O
has a [[NumberData]] internal slot, letbuiltinTag
be"Number"
. - Else if
O
has a [[DateValue]] internal slot, letbuiltinTag
be"Date"
. - Else if
O
has a [[RegExpMatcher]] internal slot, letbuiltinTag
be"RegExp"
. - Else, let
builtinTag
be"Object"
. - Let
tag
be ? Get(O
, @@toStringTag). - If Type(
tag
) is not String, lettag
bebuiltinTag
. - Return the String that is the result of concatenating
"[object "
,tag
, and"]"
.