博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
[JS相关的记录01] 那什么来面对你,面向对象编程(__proto__,prototype,constructor以及原型链)...
阅读量:7260 次
发布时间:2019-06-29

本文共 3660 字,大约阅读时间需要 12 分钟。

总是听说面向对象,类,继承,__proto__,prototype,constructor.......于是乎小整理一下。

首先说,JS里的继承是怎么弄的呢?

首先创建类(Person)

var Person = {    male: 0,    age:0,    name:'nothing',    say:function(){        console.log('Hello World');    }}

如何创建一个人呢?

var createPerson = function(){    return Object.create(Person);}

创建学生

var Student = createPerson();Student.say() //Hello WorldStudent.__proto__ === Person //trueStudent.constructor === Person //Student的构造器还是Object

从这个可以看出什么呢?可以看出所谓的继承,就是下面的代码而已:

SSSSS.__proto__ = BBBBB

但是呢?也没有prototype啥关系嘛,因为压根就和他没关系,好像也不太好,换一种写法好了。

function Person (props){    this.name = props.name || 'nothing';    this.male = props.male || 0;    this.age = props.age || 0;    this.say = function(){        console.log('Hello world!');    }}

继续创建student

var Student = new Person();Student.__proto__ === Person.prototype  //trueStudent.constructor === Person //trueStudent.say() //Hello world!

从上面代码可以看出,Student继承了Person.

如果我们想改变一下呢?

Student.say = function(){    console.log('Hello teacher, my name is ' + this.name);//Hello teacher, my name is nothing}

那好,再创建一个coder类

var Coder = new Person();Coder.say(); //Hello world!

这个不错嘛,这样在想创建Coder的子类,js和html,那就修改一下代码

function Coder (props){    Person.call(this,props);    this.tip = props.tip?props.tip.toUpperCase():'';    this.intro = function(){        console.log('I know '+(this.tip?this.tip:'nothing'));    }    this.say= function(){        console.log('hello, my name is ' + this.name);    }}var JSer = new Coder({    name:'Tony',    age:26,    tip:'js'});var htmler = new Coder({    name:'Jermy',    age:26,    tip:'html'});JSer.say();    //hello, my name is Tonyhtmler.say();  //hello, my name is JermyJSer.intro();  //I know JShtmler.intro();//I know HTML

这样得到了我们想要的结果,验证一下继承关系:

JSer instanceof Coder; //truehtmler instanceof Coder;//trueCoder instanceof Person;//false

这样就不好了,为什么不是继承关系呢?查看一下Coder情况如何?

Coder.__proto__ === Person.prototype; //falseCoder.__proto__  //function () { [native code] }

看来问题就出在这里,写一个中间函数补充一下?

var pass = function(child,parent){    var F = function(){};    F.prototype = Parent.prototype;    Child.prototype = new F();    Child.prototype.constructor = Child;}

为了实现这一点,参考道爷(就是发明JSON的那个道格拉斯)的代码,中间对象可以用一个空函数F来实现,大神写的代码,就是特么让人深思。

仔仔细细想了下,我个人是这么理解的。
首先定义空函数这个不用解释,然后把这个空函数的原型指向为Parent的原型,然后再把Child的原型指向这个新的F对象,一个完美传递;
最后,在把Child原型的构造方法定义成Child;
华丽的转身,结果如下:

function Coder (props){    Person.call(this,props);    this.tip = props.tip?props.tip.toUpperCase():'';    this.intro = function(){        console.log('I know '+(this.tip?this.tip:'nothing'));    }    this.say= function(){        console.log('hello, my name is ' + this.name);    }}var pass = function(Child,Parent){    var F = function(){};    F.prototype = Parent.prototype;    Child.prototype = new F();    Child.prototype.constructor = Child;}pass(Coder, Person);var JSer = new Coder({    name:'Tony',    age:26,    tip:'js'});var htmler = new Coder({    name:'Jermy',    age:26,    tip:'html'});JSer.say();    //hello, my name is Tonyhtmler.say();  //hello, my name is JermyJSer.intro();  //I know JShtmler.intro();//I know HTMLJSer instanceof Coder; //truehtmler instanceof Coder;//trueCoder instanceof Person;//false

结果还是不对,于是我又在大神的肩膀上垫了一下脚。

var pass = function(Child,Parent){    var F = function(){};    F.prototype = Parent.prototype;    Child.__proto__ = new F();    Child.__proto__.constructor = Child;}

结果就正确了......

又查了一下,总结一下:

  1. 所有的对象都有__proto__属性,该属性对应该对象的原型.

  2. 所有的函数对象都有prototype属性,该属性的值会被赋值给该函数创建的对象的_proto_属性.

  3. 所有的原型对象都有constructor属性,该属性对应创建所有指向该原型的实例的构造函数.

  4. 函数对象和原型对象通过prototype和constructor属性进行相互关联.

虽说弄懂了些表面的东西,实际上最主要的原因还是没明白,那就是原型链到底有什么用呢?

好了,以上就是今天总结的一些内容,希望相互学习帮助,能够在未来更好的工作生活。

信息来源:

(↓相关一些对我帮助很大,Git的学习就是在这里看的,说的很详细也很生动↓)

转载地址:http://iokdm.baihongyu.com/

你可能感兴趣的文章
node.js
查看>>
Vue 过渡实现轮播图
查看>>
使用npm发布项目
查看>>
关于NodeJS配置HTTPS服务、阿里云申请HTTPS证书
查看>>
Shortest Distance from All Buildings
查看>>
javascript之作用域
查看>>
1.1.linux命令.概要学习
查看>>
Jupyter介绍和使用
查看>>
在2019年,如何成为更好的Node.js开发者?
查看>>
国内云计算厂商众生相:四大阵营十几家企业生存盘点
查看>>
为了云,阿里、腾讯和百度一年花了多少钱?
查看>>
无服务器计算的黑暗面:程序移植没那么容易
查看>>
我在ThoughtWorks中的敏捷实践
查看>>
Universal Windows Platform(UWP)应用的窗口特性
查看>>
最新2018年全球DevOps薪资报告:行业和团队选择指南
查看>>
Visual Studio 15.4发布,新增多平台支持
查看>>
Swift和Objective-C的运行时编程
查看>>
OneAPM挂牌新三板,续写ITOM新篇章
查看>>
KubeEdge:开源的Kubernetes原生边缘计算框架
查看>>
Stefan Tilkov:跳过单体应用,从微服务开始
查看>>