• 售前

  • 售后

热门帖子
入门百科

js中实现继续的五种方法

[复制链接]
饺子姑娘 显示全部楼层 发表于 2021-10-25 19:46:29 |阅读模式 打印 上一主题 下一主题
借用构造函数


这种技术的根本思想很简单,就是在子类型构造函数的内部调用超类型的构造函数。别的,函数只不外是在特定情况中实验代码的对象,因此通过利用apply()和call()方法也可以在新创建的对象上实验构造函数。
  1. function Box(name){
  2. this.name = name
  3. }
  4. Box.prototype.age = 18
  5. function Desk(name){
  6. Box.call(this, name) // 对象冒充,对象冒充只能继承构造里的信息
  7. }
  8. var desk = new Desk('ccc')
  9. console.log(desk.name)   // --> ccc
  10. console.log(desk.age)    // --> undefined
复制代码
从中可以看到,继承来的只有实例属性,而原型上的属性是访问不到的。这种模式办理了两个题目,就是可以传参,可以继承,但是没有原型,就没有办法复用。
组合继承
  1. function Box(name){
  2. this.name = name
  3. }
  4. Box.prototype.run = function (){
  5. console.log(this.name + '正在运行...')
  6. }
  7. function Desk(name){
  8. Box.call(this, name) // 对象冒充
  9. }
  10. Desk.prototype = new Box() // 原型链
  11. var desk = new Desk('ccc')
  12. console.log(desk.name)   // --> ccc
  13. desk.run()         // --> ccc正在运行...
复制代码
这种继承方式的思绪是:用利用原型链的方式来实现对原型属性和方法的继承,而通过借用构造函数来实现对实例属性的继承。
原型式继承


原型式继承:是借助原型可以基于已有的对象创建新对象,同时还不必因此创建自界说类型。讲到这里必须得提到一个人,道格拉斯·克罗克福德在2006年写的一篇文章《Prototype inheritance in Javascript》(Javascript中的原型式继承)中给出了一个方法:
  1. function object(o) {   //传递一个字面量函数
  2. function F(){}     //创建一个构造函数
  3. F.prototype = o;    //把字面量函数赋值给构造函数的原型
  4. return new F()     //最终返回出实例化的构造函数
  5. }
复制代码
看如下的例子:
  1. function obj(o) {
  2. function F (){}
  3. F.prototype = o;
  4. return new F()
  5. }
  6. var box = {
  7. name: 'ccc',
  8. age: 18,
  9. family: ['哥哥','姐姐']
  10. }
  11. var box1 = obj(box)
  12. console.log(box1.name)   // --> ccc
  13. box1.family.push('妹妹')
  14. console.log(box1.family)  // --> ["哥哥", "姐姐", "妹妹"]
  15. var box2 = obj(box)
  16. console.log(box2.family)  // --> ["哥哥", "姐姐", "妹妹"]
复制代码
因为上述的代码的实现逻辑跟原型链继承很雷同,所以里面的引用数组,即family属性被共享了。
寄生式继承
  1. function obj(o) {
  2. function F (){}
  3. F.prototype = o;
  4. return new F()
  5. }
  6. function create(o){
  7. var clone = obj(o)   // 通过调用函数创建一个新对象
  8. clone.sayName = function(){   // 以某种方式来增强这个对象
  9.   console.log('hi')
  10. }
  11. return clone   // 返回这个对象
  12. }
  13. var person = {
  14. name: 'ccc',
  15. friends: ['aa','bb']
  16. }
  17. var anotherPerson = create(person)
  18. anotherPerson.sayName()   // --> hi
复制代码
这个例子中的代码基于person返回一个新对象————anotherPerson。新对象不但具有person的所有属性和方法,而且还有本身的sayHi()方法。在重要考虑对象而不是自界说类型和构造函数的情况下,寄生式继承也是一种有用的模式。利用寄生式继承来为对象添加函数,会由于不能做到函数复用而低落效率,这一点与构造函数模式雷同。
寄生组合式继承


前面说过,组合继承是Javascript最常用的继承模式,不外,它也有本身的不敷。组合继承最大的题目就是无论什么情况下,都会调用过两次超类型构造函数:一次是在创建子类型原型的时间,另一次是在子类型构造函数内部。没错,子类型终极会包含超类型对象的全部实例属性,但我们不得不在调用子类型构造函数时重写这些属性,再来看一下下面的例子:
  1. function SuperType(name){
  2. this.name = name;
  3. this.colors = ['red','black']
  4. }
  5. SuperType.prototype.sayName = function (){
  6. console.log(this.name)
  7. }
  8. function SubType(name, age){
  9. SuperType.call(this, name) // 第二次调用SuperType
  10. this.age = age
  11. }
  12. SubType.prototype = new SuperType() // 第一次调用SuperType
  13. SubType.prototype.constructor = SubType
  14. SubType.prototype.sayAge = function (){
  15. console.log(this.age)
  16. }
复制代码
第一次调用SuperType构造函数时,SubType.prototype会得到两个属性:name和colors。他们都是SuperType的实例属性,只不外现在位于SubType的原型中。当调用SubType构造函数时,又会调用一次SuperType构造函数,这个一次又在新对象上创建了实例属性name和colors。于是,这两个属性就屏蔽了原型中的两个同名属性。即有两组name和colors属性:一组在实例上,一组在原型上。这就是调用两次SuperType构造函数的效果。办理这个题目的方法就是————寄生组合式继承。
所谓寄生组合式继承,即通过借用构造函数来继承属性,通过原型链的混成形式来继承方法。其背后的根本思绪是:不必为了制定子类型的原型而调用超类型的构造函数,我们所必要的无非就是超类型原型的一个副本而已。本质上,就是利用寄生式继承来继承超类型的原型,然后再将效果指定给子类型的原型。寄生组合式继承的根本模式如下:
  1. function object(o) {
  2. function F (){}
  3. F.prototype = o;
  4. return new F()
  5. }
  6. function inheritPtototype(subType, superType){
  7. var prototype = object(superType.prototype) // 创建对象
  8. prototype.constructor = subType       // 增强对象
  9. subType.prototype = prototype        // 指定对象
  10. }
  11. function SuperType(name){
  12. this.name = name
  13. this.colors = ['red', 'white']
  14. }
  15. SuperType.prototype.sayName = function(){
  16. console.log(this.name)
  17. }
  18. function SubType(name,age){
  19. SuperType.call(this,name)
  20. this.age = age
  21. }
  22. inheritPtototype(SubType, SuperType)
  23. SubType.prototype.sayAge = function(){
  24. console.log(this.age)
  25. }
  26. var instance = new SubType('ccc', 18)
  27. instance.sayName()   // --> ccc
  28. instance.sayAge()    // --> 18
  29. console.log(instance)
复制代码
控制台打印出的布局:

详细的图解:

这个例子的高效率提现在它值调用了一次SuperType构造函数,而且因此避免了在SubType.prototype上面创建不必要的、多余的属性。与此同时,原型链还能保持不变;因此,还能够正常利用instanceof和isPrototypeOf()。这也是许多大厂用的继承方式。
以上就是js中实现继承的五种方法的详细内容,更多关于js 实现继承的资料请关注脚本之家别的相干文章!

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?立即注册

x

帖子地址: 

回复

使用道具 举报

分享
推广
火星云矿 | 预约S19Pro,享500抵1000!
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

草根技术分享(草根吧)是全球知名中文IT技术交流平台,创建于2021年,包含原创博客、精品问答、职业培训、技术社区、资源下载等产品服务,提供原创、优质、完整内容的专业IT技术开发社区。
  • 官方手机版

  • 微信公众号

  • 商务合作