全网整合营销服务商

电脑端+手机端+微信端=数据同步管理

免费咨询热线:400-708-3566

JavaScript用构造函数如何获取变量的类型名

使用 typeof 获取基本的类型

看到题目的第一眼,有些同学可能会想到 typeof 运算符,在JavaScript语言中,给出了使用 typeof 运算符来获取基本的类型名.(注意不是基本类型)

这是 typeof 的全部用法

01-typeof.htm

console.log('typeof of 10 ~~~~' +typeof 10);
console.log('typeof of "a" ~~~~' +typeof 'a');
console.log('typeof of true ~~~~' +typeof true);
console.log('typeof of {} ~~~~' +typeof {});
console.log('typeof of /123/ ~~~~' +typeof /123/);
console.log('typeof of function(){} ~~~~' +typeof function(){});
console.log('typeof of undefined ~~~~' +typeof undefined);
console.log('typeof of null ~~~~' +typeof null);

这是结果

按照上面的打印结果,总结出下面要注意的几点

typeof (引用类型) 除了函数, 都是 'object',比如 typeof /123/

typeof null 为'object'

typeof undefined 为 'undefined',通常, 如果使用两等号, null == undefined 为真.

转换为数字的常见用法 "10"-0, 如果没有转换成功,返回NaN,由于NaN 的一个特性: NaN != NaN ,故判断转换成功与否的常见做法: (这也是我参见 jQuery的源码发现的,jQuery源码读100遍都不为过)

("10x" - 0) == ("10x" - 0);
 // 结果为假! 

使用jQuery中的方法$.type()

现在看看jQuery是怎么做的

// 先申明一个对象,目的是用来做映射
var class2type = {};
// 申明一个core_toString() 的方法,得到最原始的toString() 方法,因为在很多对象中,toStrintg() 已经被重写 
var core_toString() = class2type.toString;
// 这里为 toStrintg() 后的结果和类型名做一个映射,申明一个core_toString() 后的结果,而值就是类型名
jQuery.each("Boolean Number String Function Array Date RegExp Object Error".split(" "), function(i, name) {
 class2type[ "[object " + name + "]" ] = name.toLowerCase();
});

因为 Object.prototype.toString() 方法调用结果如下

var core_toString = {}.toString;
console.log( core_toString.call(1) );
console.log( core_toString.call("11") );
console.log( core_toString.call(/123/) );
console.log( core_toString.call({}) );
console.log( core_toString.call(function(){}) );
console.log( core_toString.call([]) );
console.log( core_toString.call(true) );
console.log( core_toString.call(new Date()) );
console.log( core_toString.call(new Error() ));
console.log( core_toString.call(null) );
console.log( core_toString.call(undefined) );
console.log( String(null) );
console.log( String(undefined) );

上面的打印结果与

class2type[ "[object " + name + "]" ] = name.toLowerCase();

不谋而合!

这是jQuery.type 的核心方法

type: function( obj ) {
 if ( obj == null ) {
 return String( obj );
 }
 // Support: Safari <= 5.1 (functionish RegExp)
 return typeof obj === "object" || typeof obj === "function" ?
 class2type[ core_toString.call(obj) ] || "object" :
 typeof obj;
},

注意,为什么把 null 或者 undefined 单独讨论呢,因为 在一些版本浏览器中

console.log(core_toString.call(null));
console.log(core_toString.call(undefined));

这是会报错的!

如果是对象类型,另:由于 在一些低版本的浏览器中,typeof /123/ 会返回的是 "function" 而不是 "object",所以这里要判断是否是函数,要明白 这里的 typeof obj === function 不是为了函数讨论的,因为函数本身就可以通过typeof 来得到类型.

typeof obj === "object" || typeof obj === "function" ?
 class2type[ core_toString.call(obj) ]

就直接返回class2type 中键值对的结果,,如果不是,那么一定就是基本类型, 通过 typeof 就可以啦.

class2type[ core_toString.call(obj) ] || "object" :
// 这是防止一些未知情况的,如果未取到,就返回object

但是 jQuery.type 有一个很大的缺陷

这是一个自定义类型

function Person(){
 this.name = 'pawn';
}
var p = Person.toString();

// 注意,这里会打印 [object Object],通过上面的方法,无法得到精确的自定义类型

这也是 它的一个大缺陷了!

下面,我们通过构造函数的方式来获取精确类型

通过构造函数来获取类型

这种方式 是蒋坤老师( jk ) 教会我的,非常感谢他.

在理解这个方法之前,需要理解两个点

prorotype 原型属性

我们知道,任何对象或者函数都直接或者间接的继承自Object 或者 Function, (其实最终Function 是继承自 Object 的,这属于原型链的知识了)。那么,任何一个对象都具有原型对象 __proto__ (这个对象只在chrome 和 firefox 暴露,但是在其他浏览器中也是存在的),这个原型对象就是这个对象的构造函数的原型属性(这里可能有点绕).


由于 任何函数都具有 原型属性prototype,并且这个原型属性具有一个默认属性 constructor,它是这个函数的引用,看下面的代码

function Person(){
 this.name = 'pawn';
 }
 console.log(Person.prototype.constructor === Person);

​发现,这两个东西其实一个东西

但是,在某些情况下,需要这么写

function Person(){
 this.name = 'pawn';
 }
 Person.protype = {
 XX: ... ,
 xx: ... ,
 ...
 }

这么做,就会覆盖原本的 protype 方法,那么construcor 就不存在了,这是,必须要显示的申明这个对象

Person.protype = {
 construction: Person,
 XX: ... ,
 xx: ... ,
 ...
 }

在jQuery的中,就是这么做的,

jQuery.fn = jQuery.prototype = {
 constructor: jQuery,
 init: function( selector, context, rootjQuery ) {
 var match, elem;

关于 jQuery对象封装的方式 也是非常值得研究

Function.prototype.toString()

注意,这里已经不是熟悉 [object Object],而是 已经重写了.

也就是,如果调用一个函数的toString() 方法.那么就会打印这个函数的函数体.

好了,经过上面两个步骤,你明白我要做什么了吗?

如何通过构造函数来获得变量的类型?

判断是否是基本类型

var getType = function(obj){
 if(obj == null){
 return String(obj);
 }
 if(typeof obj === 'object' || typeof obj === 'fucntion'){
 ...
 }else{
 // 如果不是引用类型,那么就是基本类型
 return typeof obj
 }
 }

如果是对象或者函数类型

function Person(){
 this.name = 'pawn';
 }
 var p = new Person();
 console.log(p.constructor);

现在要做的事 : 如何将Person 提取出来呢?

毋庸置疑,字符串切割那一套肯定可以办到,但是太 low 啦!

这里,我使用正则将Person提取出来

var regex = /function\s(.+?)\(/
function Person(){
 this.name = 'pawn';
 }
 var p = new Person();
 var c = p.constructor
 var regex = /function\s(.+?)\(/;
 console.log('|' + regex.exec(c)[1] + '|');

使用name

其实,除了上面的正则,每个函数还有一个name属性,返回函数名,但是ie8 是不支持的.

因此上面的代码可以写为:

var getType = function(obj){
 if(obj == null){
 return String(obj);
 }
 if(typeof obj === 'object' || typeof obj === 'function'){ 
 var constructor = obj.constructor;
 if(constructor && constructor.name){
 return constructor.name;
 }
 var regex = /function\s(.+?)\(/;
 return regex.exec(c)[1];
 }else{
 // 如果不是引用类型,那么就是基本;类型
 return typeof obj;
 }
};

但是上面的代码太丑啦,将其简化

简化

var getType = function(obj){
 if(obj == null){
 return String(obj);
 }
 if(typeof obj === 'object' || typeof obj === 'function'){ 
 return obj.constructor && obj.constructor.name.toLowerCase() || 
 /function\s(.+?)\(/.exec(obj.constructor)[1].toLowerCase();
 }else{
 // 如果不是引用类型,那么就是基本类型
 return typeof obj;
 }
};

还是比较麻烦,继续简化

var getType = function(obj){
 if(obj == null){
 return String(obj);
 }
 return typeof obj === 'object' || typeof obj === 'function' ?
 obj.constructor && obj.constructor.name && obj.constructor.name.toLowerCase() ||
 /function\s(.+?)\(/.exec(obj.constructor)[1].toLowerCase():
 typeof obj;
};

好了,已经全部弄完了,写个代码测试一下:

function Person(){
 this.name = 'pawn';
}
var p = new Person();

console.log(getType(p));
console.log(getType(1));
console.log(getType("a"));
console.log(getType(false));
console.log(getType(/123/));
console.log(getType({}));
console.log(getType(function(){}));
console.log(getType(new Date()));
console.log(getType(new Error()));
console.log(getType( null));
console.log(getType( undefined));

总结

好了,以上就是关于如何获取变量的类型名的全部介绍了,希望本文的内容能对你提供帮助。如果有疑问大家可以留言交流。


# js  # 变量类型  # js获取变量的类型  # javascript  # 构造函数  # JS特殊函数(Function()构造函数、函数直接量)区别介绍  # JS中的构造函数详细解析  # Javascript 使用function定义构造函数  # JavaScript中的普通函数与构造函数比较  # 深入理解javascript构造函数和原型对象  # Javascript的构造函数和constructor属性  # JavaScript构造函数详解  # Js检查变量类型的代码()  # js 变量类型转换常用函数与代码[比较全]  # js判断undefined变量类型使用typeof  # 这是  # 如果不是  # 好了  # 就会  # 自定义  # 这么做  # 就可以  # 的是  # 都是  # 运算符  # 判断是否  # 这也是  # 器中  # 我要  # 出了  # 就不  # 做什么  # 对你  # 将其  # 它是 


相关文章: 家具网站制作软件,家具厂怎么跑业务?  免费ppt制作网站,有没有值得推荐的免费PPT网站?  h5在线制作网站电脑版下载,h5网页制作软件?  如何在万网自助建站中设置域名及备案?  如何在阿里云虚拟服务器快速搭建网站?  如何选择高效稳定的ISP建站解决方案?  开心动漫网站制作软件下载,十分开心动画为何停播?  如何生成腾讯云建站专用兑换码?  定制建站策划方案_专业建站与网站建设方案一站式指南  网站app免费制作软件,能免费看各大网站视频的手机app?  建站之星如何快速解决建站难题?  制作旅游网站html,怎样注册旅游网站?  如何选择高效可靠的多用户建站源码资源?  建站之星会员如何解锁更多建站功能?  正规网站制作公司有哪些,目前国内哪家网页网站制作设计公司比较专业靠谱?口碑好?  北京网页设计制作网站有哪些,继续教育自动播放怎么设置?  如何高效利用200m空间完成建站?  建站DNS解析失败?如何正确配置域名服务器?  如何通过云梦建站系统实现SEO快速优化?  如何在云主机上快速搭建多站点网站?  广东企业建站网站优化与SEO营销核心策略指南  深入理解Android中的xmlns:tools属性  广德云建站网站建设方案与建站流程优化指南  如何用y主机助手快速搭建网站?  浅谈Javascript中的Label语句  ,制作一个手机app网站要多少钱?  如何用低价快速搭建高质量网站?  网站制作公司排行榜,四大门户网站排名?  建站主机如何选?性能与价格怎样平衡?  宝塔面板创建网站无法访问?如何快速排查修复?  如何获取上海专业网站定制建站电话?  php8.4新语法match怎么用_php8.4match表达式替代switch【方法】  岳西云建站教程与模板下载_一站式快速建站系统操作指南  建站之星Pro快速搭建教程:模板选择与功能配置指南  大连网站制作费用,大连新青年网站,五年四班里的视频怎样下载啊?  企业微网站怎么做,公司网站和公众号有什么区别?  股票网站制作软件,网上股票怎么开户?  如何在企业微信快速生成手机电脑官网?  设计网站制作公司有哪些,制作网页教程?  宝塔建站后网页无法访问如何解决?  网站视频制作书签怎么做,ie浏览器怎么将网站固定在书签工具栏?  C#如何序列化对象为XML XmlSerializer用法  简历在线制作网站免费版,如何创建个人简历?  如何在阿里云虚拟主机上快速搭建个人网站?  如何高效生成建站之星成品网站源码?  香港服务器建站指南:外贸独立站搭建与跨境电商配置流程  C#如何在一个XML文件中查找并替换文本内容  如何处理“XML格式不正确”错误 常见XML well-formed问题解决方法  零基础网站服务器架设实战:轻量应用与域名解析配置指南  简历在线制作网站免费,免费下载个人简历的网站是哪些? 

您的项目需求

*请认真填写需求信息,我们会在24小时内与您取得联系。