惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

量子位
S
Securelist
MyScale Blog
MyScale Blog
Jina AI
Jina AI
罗磊的独立博客
The Cloudflare Blog
美团技术团队
博客园 - 叶小钗
阮一峰的网络日志
阮一峰的网络日志
博客园 - 三生石上(FineUI控件)
月光博客
月光博客
雷峰网
雷峰网
小众软件
小众软件
aimingoo的专栏
aimingoo的专栏
大猫的无限游戏
大猫的无限游戏
博客园 - Franky
博客园 - 聂微东
Y
Y Combinator Blog
酷 壳 – CoolShell
酷 壳 – CoolShell
freeCodeCamp Programming Tutorials: Python, JavaScript, Git & More
MongoDB | Blog
MongoDB | Blog
T
Tailwind CSS Blog
Attack and Defense Labs
Attack and Defense Labs
博客园_首页
Latest news
Latest news
Apple Machine Learning Research
Apple Machine Learning Research
Threat Intelligence Blog | Flashpoint
Threat Intelligence Blog | Flashpoint
The Hacker News
The Hacker News
G
GRAHAM CLULEY
Simon Willison's Weblog
Simon Willison's Weblog
Exploit-DB.com RSS Feed
Exploit-DB.com RSS Feed
P
Proofpoint News Feed
CTFtime.org: upcoming CTF events
CTFtime.org: upcoming CTF events
U
Unit 42
D
Docker
Webroot Blog
Webroot Blog
N
Netflix TechBlog - Medium
T
Tor Project blog
C
Cyber Attacks, Cyber Crime and Cyber Security
L
LINUX DO - 最新话题
cs.CV updates on arXiv.org
cs.CV updates on arXiv.org
The Last Watchdog
The Last Watchdog
B
Blog
Recent Announcements
Recent Announcements
GbyAI
GbyAI
Microsoft Azure Blog
Microsoft Azure Blog
Security Latest
Security Latest
V2EX - 技术
V2EX - 技术
N
News | PayPal Newsroom
Microsoft Security Blog
Microsoft Security Blog

講評世界

My App Defaults 2023 读书的意义 そして、次の曲が始まるのです 从零开始的 RSSHub Docker 私有化部署指南 使用 Homebrew 安装 Typora 的 0.11.18 版本 使用 TypeScript 为 Vue 组件的 prop 标注类型 【译文】Grid 用于布局, Flexbox 用于组件 【译文】IndexedDB 为什么这么慢?如何更好的使用呢? Hello 2022 「他山之石」零贰 「他山之石」零壹 「言論」 零壹 给 icarus 主题增加所有文章的字数统计 hexo 无法在本地实时预览 JavaScript 立即调用的函数表达式(IIFE) 解决 nvm 无法在 arm 架构下安装 V15 以下的 node 版本 的问题 m1 芯片安装 nvm 提示 command not found Cookie?小饼干! 使用 RSS 在推荐算法中获取主动权
如何在 JavaScript 完美的确定一个数据的类型
Moeyua · 2021-11-03 · via 講評世界

JavaScript 中有三种方式来确定一个数据的类型:

  • typeof 运算符
  • instanceof 运算符
  • Object.prototype.toString() 方法
    这里就来简单梳理一下这三种方式的优劣,同时得出一个能够完美判断数据类型的方法。

typeof

typeof 很简单,下面是一个简单的例子:

let a = 'foo';
let b = 1;
let c = true;
typeof a    // "string"
typeof b    // "number"
typeof c    // "boolean"

使用 typeof 判断『原始类型』(数值、字符串、布尔值)时分别返回 numberstringboolean。『合成类型』(对象、数组、函数)分别返回 objectobjectfunction

let a = {foo = 'bar'};
let b = ['foo', 'bar'];
let c = function(foo) {
    return foo + 'bar'
}
typeof a    // "object"
typeof b    // "object"
typeof c    // "function"

而对于 undefinednull 这两种类型,typeof 能够正常判断 undefined,但是 typeof null 会返回 object

let a = undefined;
let b = null;

typeof a    // "undefined"
typeof b    // "object"

出现这种情况的原因时最初版的 JavaScript 并没有将 null 单独拿出来作为一个数据类型,只是作为 object 类型的一种,后来将 null 单独拿了出来,但是为了兼容以前的旧的代码,就没有改变 typeof null 的返回值。

可见 typeof 大部分情况下确实能够准确判断出数据类型,但是对于 Arraynull 就会失效。

instanceof

instanceof 运算符返回一个布尔值,表示对象是否为某个构造函数的实例。根据这一特点我们就能够使用该运算符判断数据类型。

let a = {foo = 'bar'};
let b = ['foo', 'bar'];
let c = function(){};

a instanceof Object     // true
b instanceof Array      // true
c instanceof Function   // true

如上面的代码所示,instanceof 能够区分对象的各种类型,但是需要注意的是,instanceof 只能判断对象类型,对于 numberstringbooleanundefinednull 这几种类型是无法判断的。

Object.prototype.toString()

Object.prototype.toString() 方法的作用是返回一个对象的字符串形式,默认情况下返回类型字符串。不同数据类型的 toString 方法返回如下

数据类型返回值
数字[object Number]
字符串[object String]
布尔值[object Boolean]
数组[object Array]
函数[object Function]
undefined[object Undefined]
null[object Null]
arguments 对象[object Arguments]
Error 对象[object Error]
Date 对象[object Date]
RegExp 对象[object RegExp]
其他对象[object Object]

那么基于这一特性,我们可以近乎完美的确定一个常见数据的类型:

var type = function (o){
  var s = Object.prototype.toString.call(o);
  return s.match(/\[object (.*?)\]/)[1].toLowerCase();
};

type({});// "object"
type([]); // "array"
type(5); // "number"
type(null); // "null"
type(); // "undefined"
type(/abcd/); // "regex"
type(new Date()); // "date"

需要注意的是,由于实例对象可能会改写 Object.prototype.toSring,所以我们直接使用 Object.prototype.toSring,使用函数的 Call 方法在任意值上调用这个方法。

在上面这个type函数的基础上,还可以加上专门判断某种类型数据的方法。

var type = function (o){
  var s = Object.prototype.toString.call(o);
  return s.match(/\[object (.*?)\]/)[1].toLowerCase();
};

['Null',
 'Undefined',
 'Object',
 'Array',
 'String',
 'Number',
 'Boolean',
 'Function',
 'RegExp'
].forEach(function (t) {
  type['is' + t] = function (o) {
    return type(o) === t.toLowerCase();
  };
});

type.isObject({}) // true
type.isNumber(NaN) // true
type.isRegExp(/abc/) // true