通用类型检测应优先使用Object.prototype.toString.call()获取精确内部标签,再辅以安全边界判断;它可正确识别null、undefined、DOM元素及跨iframe对象,且避免constructor篡改和上下文失效问题。

直接用 typeof 或 instanceof 判断类型容易出错,比如 typeof null === 'object'、Array instanceof Object === true 却无法区分数组和普通对象。通用类型检测函数的核心是:**优先使用 Object.prototype.toString.call() 获取精确的内部标签,再辅以安全的边界判断**。
用 toString 获取标准内部类型标签
Object.prototype.toString 是最可靠的方式,它返回形如 "[object Array]"、"[object Date]" 的字符串,不受原型篡改影响:
- 对任意值调用
Object.prototype.toString.call(value),得到标准化的类型标识 - 提取中括号内的关键词(如
Array、Promise、Map),统一转为小写便于比对 - 注意:原始值(
string、number等)也会正确返回"[object String]",无需特殊处理
封装成可复用的检测函数
推荐按需导出多个具名函数,语义清晰且 tree-shakable:
PigX UI Pro 前端开发指南 - Vue 3 + TypeScript + Element Plus。当用户提到 PigX UI、PigX 前端、lgb-mgui 项目、Vue 3 企业级后台开发、Element Plus 后台开发时使用此技能。
-
isString(val)→toString.call(val) === '[object String]' -
isArray(val)→toString.call(val) === '[object Array]' -
isFunction(val)→typeof val === 'function'(toString对箭头函数也返回Function,但typeof更轻量) -
isPlainObject(val)→ 先确认是Object,再检查val.constructor === Object或getPrototypeOf(val) === Object.prototype
处理特殊值与边界情况
健壮性体现在对 null、undefined、宿主对象(如 DOM 元素)、跨 iframe 对象的兼容:
-
null和undefined经toString.call()分别返回"[object Null]"和"[object Undefined]",可直接识别 - DOM 元素在多数浏览器中返回
"[object HTMLDivElement]"等,可用isElement(val)判断val.nodeType === 1更稳妥 - 跨 iframe 的数组或正则,
toString.call()仍能正确识别(因它不依赖当前执行环境的构造函数)
避免常见陷阱
不要依赖不可靠的特征:
- 不用
val.constructor === Array—— 构造函数可能被覆盖或跨 iframe 失效 - 不用
Array.isArray()以外的“伪数组”检测(如hasOwnProperty或length属性)—— 类数组对象(arguments、NodeList)不是数组 - 不混用
typeof和instanceof判断复合类型(如instanceof Promise在不同上下文可能失败)
不复杂但容易忽略:把类型检测逻辑收拢到一个模块,所有业务代码只调用这些函数,后续维护和补充新类型(如 isBigInt、isAsyncFunction)就非常集中。

















