web前端开发中关于面向对象(三)
来源:互联网 发布:linux修改tomcat内存 编辑:程序博客网 时间:2024/06/07 01:07
在面向对象前篇中提到过原型的概念,说到原型,便又延伸出了关于原型的一个知识点——原型链。也许作为一名专业的前端开发人员来说,明白原型链的含义以及用法,但对于前端的爱好者和在校大学生而言,对于原型链的概念可能是第一次听说,所以,今天就和大家学习一下原型链。 一、含义 实例对象和原型对象组成的一条链式结构,链式结构之间通过__proto__链接起来,这条链就成为原型链。 例:
function Person(name){ this.name=name;}Person.prototype.showName=function(){ console.log(this.name);}var p=new Person("Sue");//以上函数的原型链p-->Person.prototype-->Object.prototype-->null//其中,-->表示__proto__,该原型链的含义为:p.__proto__指向其构造函数的原型Person.prototype,而构造函数的原型默认是Object的实例,因而指向Object.prototype,之后便结束为空,至于原理,请参照上篇web前端开发中关于面向对象(二)进行理解。
通过几次的实验和验证可以发现,原型链的末端都是Object.prototype,所有的对象都直接或间接的继承Object。 二、精确判断数据类型的方法 判断数据类型不仅仅有typeof一种方式,且typeof方法只能判断一般的数据类型,得到的结果较为模糊,不够精准。若想要精确的判断数据类型,需用到Object.prototype上的toString方法。使用Object.prototype.toString方法判断数据类型需要改变this的指向,因而需要配合call一起使用。typeof与Object.prototype.toString的区别:
var arr= []; var fn = function(){}; var str = "str"; var obj = {}; var date = new Date(); var regExp = new RegExp(); console.log("toString判断结果:"+Object.prototype.toString.call(arr)); console.log("typeof判断结果:"+typeof arr); console.log('------------------') console.log("toString判断结果:"+Object.prototype.toString.call(fn)); console.log("typeof判断结果:"+typeof fn); console.log('------------------') console.log("toString判断结果:"+Object.prototype.toString.call(str)); console.log("typeof判断结果:"+typeof str); console.log('------------------') console.log("toString判断结果:"+Object.prototype.toString.call(obj)); console.log("typeof判断结果:"+typeof obj); console.log('------------------') console.log("toString判断结果:"+Object.prototype.toString.call(date)); console.log("typeof判断结果:"+typeof date); console.log('------------------') console.log("toString判断结果:"+Object.prototype.toString.call(regExp)); console.log("typeof判断结果:"+typeof regExp);/*结果: toString判断结果:[object Array] typeof判断结果:object ------------------ toString判断结果:[object Function] typeof判断结果:function ------------------ toString判断结果:[object String] typeof判断结果:string ------------------ toString判断结果:[object Object] typeof判断结果:object ------------------ toString判断结果:[object Date] typeof判断结果:object ------------------ toString判断结果:[object RegExp] typeof判断结果:object*/
三、函数和Function的关系 函数,在上篇已经提到过,在不同的情况下所担任的角色就各不相同,可作为构造函数、普通函数等。而普通函数在使用字面量声明时就是构造函数,`var fn=new Function(){}`有时候也可是构造函数。那么,函数和Function两者之间又有何关联?仅仅使用文字是解释不太明白的,还是让代码来告诉大家。
function foo(){...}console.log(foo.__prototype==Function.prototype);//trueconsole.log(Object.__proto__==Function.prototype);//trueconsole.log(Function.__proto__==Function.prototype);//true/*原型链:foo-->Function.prototype-->Object.prototype-->nullobject-->Function.prototype-->Object.prototype-->nullFunction-->Function.prototype*/
四、关于defineProperty Object中具有一个方法:defineProperty,该方法是定义特性。该方法具有三个参数。 (1)第一个参数:目标对象 (2)第二个参数:需要定义属性和方法的名字 (3)第三个参数:目标属性所拥有的特性,必须是对象 例:
var a={};Object.defineProperty(a,"b",{ value:1, writable:true, configurable:true, enumerable:true});
以上例子的意思是:为对象a定义了一个属性,该属性为b,且为b赋值为1。defineProperty中第三个参数,对象中各个属性的含义: (1)value:属性的值 (2)writable:属性值是否可以被重写,默认为false,若为true,则可以被重写 (3)configurable:总开关,默认为false。总开关一旦为false,value、writeable、configurable就不可被重设 (4)enumerable:是否可以在for/in中循环遍历,默认为false defineProperty方法的第三个参数对象中还有两个属性,get和set,若使用get和set者两个属性,则就不需要再同时使用以上四个属性。 (1)get:获取值 (2)set:赋值 例:
Object.defineProperty(a,"b",{ set:function(val){}, get:function(){}});
我们可以通过defineProperty中的set和get者两个属性来实现数据的双向绑定。 例:
<input type="text" v-model="val"/><p v-model="val"></p><script> var inp=document.getElementsByTagName("input")[0]; var p=document.getElementsByTagName("p")[0]; var obj={}; Object.defineProperty(obj,"val",{ get:function() return inp.value; }, set:function(val){ p.innerHtml=val; inp.value=val; } }); inp.oninput=function(){ obj.val=inp.value; }</script>
五、实例判断 如何判断对象是否是构造函数的实例?instanceof:判断对象是否是构造函数的实例。如果构造函数的原型在原型链上,那么原型链开始的那个实例是所有原型所属的构造函数的实例。 例:
function Person(name){ this.name=name;}Person.prototype.showName=function(){ console.log(this.name);}function Student(num){ this.num=num;}Student.prototy=new Person("Sue");var stu=new Student(90);console.log(stu instanceof Student);//trueconsole.log(stu instanceof Person);//trueconsole.log(stu instanceof Object);//trueconsole.log(stu instanceof Function);//false//原型链://stu-->Student.prototype-->Person.prototype-->Object.prototype-->null
六、属性判断 (1)hasOwnProperty():判断对象中是否有某个属性,该方法只能判断实例对象上的属性,不能判断原型对象上的属性。 (2)in:既可以判断实例对象上的属性,又可以判断原型对象上的属性 例:
var obj=new Object();obj.info="Sue";obj.name="Mike";Object.prototype.age="20";console.log(obj.hasOwnProperty("info"));//trueconsole.log("info" in obj);//trueconsole.log(obj.hasOwnProperty("name"));//trueconsole.log("name in obj);//trueconsole.log(obj.hasOwnProperty("age"));//falseconsole.log("age" in obj);//true
判断某个属性是否在原型上的方法:
if("info" in obj &&!obj.hasOwnProperty("info")){...}
七、原型继承 在其他语言中,面向对象中也存在继承和封装。在前端开发中面向对象也存在着继承,前端将继承分为几种,今天先看一看原型继承。其实,在以上提到的知识中已经涉及到也使用到了原型继承。 例:
function Animal(name){ this.name=name;}Animal.prototype.showName={ console.log(this.name);}function Tiger(age){ this.age=age;}var tiger=new Tiger("12");
以上代码块执行的结果只会输出12。老虎是动物的一种,按照常理而言,老虎应该具有动物的特性,那么执行以上代码块,老虎应该具有姓名和年龄两个属性才是合理的,而如今只输出了年龄,那么怎样才可以在不再Tiger构造函数中添加属性而获得Animal构造函数中的name属性?这里便涉及到--继承的知识点。若想要继承Animal,则代码块为:
function Animal(name){ this.name=name;}Animal.prototype.showName={ console.log(this.name);}function Tiger(age){ this.age=age;}Tiger.prototype=new Animal("caser");var tiger=new Tiger("12");
如此,老虎便可继承Animal中的属性和方法,且它自身的方法和属性也不会被共享。这便是原型继承。但原型继承存在几个问题: (1)无法在不影响所有实例的情况下,给要继承的构造函数传参 (2)继承的构造函数中的引用类型对于所有的实例是共享的 那么,又该如何解决原型继承存在的这些问题呢?请阅读下一篇。
阅读全文
0 0
- web前端开发中关于面向对象(三)
- web前端开发中关于面向对象(一)
- web前端开发中关于面向对象(二)
- web前端开发中关于面向对象(四)
- 关于android开发中涉及到的java知识:面向对象(三)
- web前端开发中浏览器兼容问题(三)
- web前端之dojo实际应用及开发四:面向对象开发[关键](附有源码)
- Web前端开发和JS面向对象编程分享
- web前端开发笔记:JavaScript面向对象总结
- web前端之面向对象
- 前端开发之面向对象
- Web前端复习——Javasvript学习(面向对象)
- PHP面向对象开发(三)
- web前端 js面向对象思想
- web前端之JavaScript高级程序设计三:面向对象的程序设计
- [WEB前端开发]-关于Velocity中Map与List操作-解决velocity无法识别Map对象key的问题
- web 前端(三)
- 面向对象(三)
- java基础二
- 初学者java:将一个整数分解质因数
- 如何简单地安装python3并将其添加到环境变量里
- Android HIDL 官方文档(四)—— 服务与数据转换(Services & Data Transfer)
- LoRaWAN节点RTC定时器链表分析
- web前端开发中关于面向对象(三)
- 10-25 最小生成树——kruskal算法学习——经典例题及自编模版
- 如何实现点击一个下拉菜单的选项就弹出不同的输入框或者下拉菜单
- git 工作中常用命令
- 使用Ribbon实现客户端负载均衡
- hibernate整合的公共工具类---继承实现
- oracle11gserver在win10系统上面的安装和使用
- angularJS订单管理
- 无线轮播 + GridView