原型对象继承

  • 原理:原型对象的属性可以经由对象实例访问
  • 下面的例子,所含【对象继承】和【构造函数继承】,用于理解【原型属性经由对象实例访问】
//对象继承
var person = {name:"gs",age:19
}
console.log(person.prototype === undefined );
function Student(){}
Student.prototype = person;//原型属性经由对象实例访问
console.log(new Student());
//构造函数继承
function Person(){this.name = "gs";this.age = 19;
}
function Student(){this.name = "zk"
}
Student.prototype = new Person();//原型属性经由对象实例访问
var zk = new Student();
console.log(zk);

Object是顶层对象

  • 所有对象都继承自 Object.prototype,除非显示指定
  • 以对象字面量定义的对象,其 prototype 的值都被设为 Object.prototype

定义在 Object.prototype 上的方法

  • hasOwnProperty
  • propertyIsEnumerable
  • isPrototypeOf
  • valueOf | 返回对象的值表达
  • toString | 返回对象的字符串表达

valueOf

  • 每当一个操作符被用于一个对象时(自动)调用

toString

  • 在进行运算时,有可能发生类型转换
let obj = { name:"gs" };
console.log(obj+111)//;[object Object]111
console.log(obj.toString());//[object Object]
console.log(obj.valueOf());//{ "name": "gs" }

最好不要去修改 Object.prototype

最简单的一个对象继承

  • 声明一个字面量对象,相当于自动继承自 Object
  • 声明字面量对象,可以用 Object.create 方法替代,它的继承作用更加明显
  • 注意:Object.prototype 实际上值是 null
var student1 = {name:"gs"
}
var student2 = Object.create(Object.prototype,{name:{configurable:true,enumerable:true,value:"gs",writable:true,}
})

实现一个基本的对象继承

//对象继承
var person = {name:"gs",age:19
}
console.log(person.prototype === undefined );
function Student(){}
Student.prototype = person;//原型属性经由对象实例访问
console.log(new Student());

实现一个稍复杂的构造函数继承

  • 因为js中的继承是通过原型对象链来实现的,因此没有调用对象父类的构造函数
  • 所以,要注意!最好重写构造器属性,否则将被设为父类的值
function Person(school,name,age){this.school = "beijing univercity";this.name = name;this.age = age;
}
Person.prototype.sayName = function(){console.log(this.name);
}
Person.prototype.sayAge = function(){console.log(this.age);
}function Student(name,age){this.name = name;this.age = age;
}
Student.prototype = new Person();
var gs = new Student("gs",19);
console.log(gs.constructor);//Person
Student.prototype.constructor = Student;//注意!要重写构造器属性,否则将被设为父类的值
console.log(gs.constructor);//Student
Student.prototype.sayName = function(){console.log("student is "+this.name);
}
console.log(gs.sayName());
console.log(gs.sayAge());

实现一个伪类继承(构造函数窃取)

  • 实际上就是使用 call 的方式,将父类的属性“拷贝”到子类中,同时还包括了constructor属性
  • 仍然需要用prototype方式继承方法,同时还要设置constructor
function Person(school,name,age){this.school = "beijing univercity";this.name = name;this.age = age;
}
Person.prototype.sayName = function(){console.log(this.name);
}
Person.prototype.sayAge = function(){console.log(this.age);
}function Teacher(school){Person.call(this,...arguments);//因为this指向Teacher,所以constructor属性仍将是Teacherthis.school = school;//注意,新的属性,应置于继承发生之后,以做覆盖
}
var zk = new Teacher("haver","zk",23);
console.log(zk.constructor);//constructor属性正确,为Teacher
console.log(zk.sayName === undefined);//true,但是,没有继承原型方法和属性
Teacher.prototype = new Person();
var zk_2 = new Teacher("haver","zk_2",23);//没有继承原型方法
console.log(zk_2.sayName());//拿到方法了
console.log(zk_2.constructor);//Person。不是吧,constructor属性又不对了
Teacher.prototype.constructor = Teacher;
console.log(zk_2.constructor);//Teacher。使用call方式继承属性,仍然需要用prototype方式继承方法,同时还要设置constructor

父类方法被子类覆盖,如何仍然可以调用?

function Person(name,age){this.name = name;this.age = age;
}
Person.prototype.sayName = function(){console.log("father method " + this.name);
}
Person.prototype.sayAge = function(){console.log(this.age);
}function Student(){Person.call(this,...arguments);
}
Student.prototype = Object.create(Person.prototype,{constructor:{configurable:true,enumerable:true,value:Student,writable:true,}
})
Student.prototype.sayName = function(){console.log("child method");
}
Student.prototype.sayName_1 = function(){Person.prototype.sayName.call(this);//这是唯一的访问父类的方法
}
var gs = new Student("gs",20);
console.log(gs);console.log(gs.sayName_1());

创建一个没有原型对象的对象

  • 它不会发生和继承来的属性名相冲突的问题,所以它是一个完美的【哈希容器】
  • 哈希容器也可以理解为是一种映射容器,采用哈希算法(映射算法,散列算法),将不定长的数据压缩成定长的数据,这串定长值我们称为 哈希值
var obj = Object.create(null);
console.log(obj.prototype === undefined);
console.log( valueOf in obj);
console.log( toString in obj);

深入理解js中实现继承的原理和方法相关推荐

  1. 详细理解JS中的继承

    正式说继承之前,有两个相关小点: JS只支持实现继承,即继承实际的方法,不支持接口继承(即继承方法的签名,但JS中函数没签名) 所有对象都继承了Object.prototype上的属性和方法. 说继承 ...

  2. 详解js中的继承(一)

    详解js中的继承(一) 前言 准备知识 1.构造函数,实例 2.原型对象 3.构造函数,原型对象和实例的关系 继承 原型链 小结 前言 通过[某种方式]让一个对象可以访问到另一个对象中的属性和方法,我 ...

  3. 一文带你理解Java中Lock的实现原理

    转载自   一文带你理解Java中Lock的实现原理 当多个线程需要访问某个公共资源的时候,我们知道需要通过加锁来保证资源的访问不会出问题.java提供了两种方式来加锁,一种是关键字:synchron ...

  4. 深入理解Js中的this

    深入理解Js中的this JavaScript作用域为静态作用域static scope,但是在Js中的this却是一个例外,this的指向问题就类似于动态作用域,其并不关心函数和作用域是如何声明以及 ...

  5. js原型和原型链_理解JS中的原型和原型链

    导读:JavaScript中(JS)的原型和原型链是web前端开发面试中经常被问到的问题:同时,如果我们能很好的理解JS中的原型和原型链,对于控制台输出的很多信息我们也能更好的理解,而原型链也是实现继 ...

  6. 理解js中的面向对象

    目录 前言: 一点疑问: 1.封装 2.继承 原型链的查找机制 不容易理解的点: ----重点在最后---- 前言: js是一门面向对象的语言,但是又没有类的概念,虽然后来加入了class,但也就是个 ...

  7. 彻底理解js中this

    相关博文:http://blog.csdn.net/libin_1/article/details/49996815 彻底理解js中this的指向,不必硬背. 首先必须要说的是,this的指向在函数定 ...

  8. python中继承是什么意思_如何理解Python中的继承?python入门

    如何理解Python中的继承?如今,python编程语言深受企业和个人的喜爱.python开发工程师是近年来互联网行业非常热门的职业岗位之一.学习python的人除了零基础的,还有一部分是在职运维.在 ...

  9. 理解js中的this指向以及call,apply,bind方法

    <script> function a(){var user = "追梦子";console.log(this.user); //undefinedconsole.lo ...

最新文章

  1. MyBatis快速入门及深入
  2. Mathtype全文公式大小一致调整
  3. javascript 定义类(转载)
  4. 停车场管理系统c语言程序,c语言程序设计 停车场管理系统 停车场有1-20个车位号,设计一个停车场管理系统,实现停车场管理...
  5. 一个资深系统管理员的O2O实践(三)
  6. win7+opencv3.0.0+vs2010 安装及配置
  7. ae导出gif插件_AE小白必看教程,围观AE老司机如何使用AE导出gif图片
  8. 正则表达式之子表达式 ‘()’ 中表达式 '[]' 大表达式 '{}'
  9. python之HTTP处理模块urllib和urllib2
  10. android 监听fling,[安卓]Android Recycler Fling解析
  11. Linux内核学习开始
  12. 苏州真不能成为一线城市?
  13. 2021阿里巴巴校招笔试题
  14. 布法罗博士计算机专业回国人员,2020年纽约州立大学布法罗分校博士专业设置...
  15. C语言解决猴子吃桃子问题
  16. Excel数值累加操作演示(一)
  17. linux查看内存条ddr3和ddr4,怎么区分DDR3和DDR4内存条
  18. 全网搜集面食题系列专题(Redis篇)
  19. SEVERE: Could not contact [localhost:[8005]]. Tomcat may not be running.问题解决
  20. 摩拜单车服务器暂时不可用,摩拜单车无响应无法使用怎么回事?扫码解锁秒退解决方法...

热门文章

  1. [MySQL]基本数据类型及表的基本操作
  2. Edge正式版可以启用ClearType了,低分屏必开
  3. gRPC Wait for Ready
  4. 如何通过鼠标采集图片数据集
  5. TCP首部(报头)理解
  6. HTML文档的基本格式/标签/学习笔记
  7. 世界上最大的赌局?!!
  8. 【前端32_高级】正则表达式:元字符、断言、匹配模式
  9. transaction 2 failed while formatting outputs from RPC
  10. 38.【C++ 虚函数 纯虚函数 虚基类 (最全详解)】