js的继承方法小结(prototype、call、apply)(推荐)


Posted in Javascript onApril 17, 2019

js的原型继承 --  prototype

先说下什么是prorotype?

  1. js中,俗话说“一切皆对象”。用new 出来的都是函数对象;否则就是普通对象
  2. 函数对象都有prototype(原型对象);而普通对象则只有__proto__(原型指针)
  3. 函数对象的一个特点:可以实现不同类之间的方法继承
  4. 函数的子类可以共享父类的方法,而父类不能想用子类的方法
eg: (prototype的继承)
 
 //创建父类函数对象  
 function Personal(name, age) {
  this.name = name;   //父类的私有属性
  this.age = age;
  this.house = ['北京', '上海']
 }
 Personal.prototype.run = function() {  //给父类原型动态添加方法
  alert('原型方法:' + this.name + ' is running!');
 }
 var per = new Personal('小白', 24)
 per.run() //打印 --> 原型方法:小白 is running!
 
 //创建子类函数对象
 function Boy() {}
 Boy.prototype = new Personal('小黑', 19) //子类继承父类的所有属性和方法
 Boy.prototype.source = 100      //给子类添加原型属性
 Boy.prototype.printSource = function() { //给子类添加方法
  alert(this.name + '的原型方法printSouce打印成绩为:' + this.source) //小黑的原型方法printSouce打印成绩为:100
 }
 Boy.prototype.run()  //打印 --> 原型方法:小黑 is running!
 var boys = new Boy()
 boys.printSource()
 console.log(boys, '--boys---') //打印 -->19, 小黑, 100 (这里会沿着prototype向上查找到Personal的属性)

以下是关于prototype继承需要注意的点:

1.如果父类中有引用类型的属性:Array,Object等。子类继承了这些属性,并尝试改变的话,会影响到父类的属性。

//创建另外一个实例1:
   var boys1 = new Boy()
   boys1.house.push('深圳')
//打印这两个实例:
   console.log(boys, boys1)

js的继承方法小结(prototype、call、apply)(推荐)

可以看出来,当属性为引用类型时,只要有一个实例的属性做了操作,所有的实例都会受到影响。

2.该方式导致 Boy.prototype.constructor 被重写,它指向的是 Personal 而非 Boy。因此你需要手动将 Boy.prototype.constructor 指回 Boy。

Boy.prototype = new Personal();
Boy.prototype.constructor === Personal; // true

// 重写 Boy.prototype 中的 constructor 属性,指向自己的构造函数 Boy
Boy.prototype.constructor = Boy;

3.因为 Boy.prototype = new Personal(); 重写了 Boy 的原型对象,所以 printSource 放在重写原型对象之前会被覆盖掉,因此给子类添加原型方法必须在替换原型之后(eg是没有被覆盖的)。

function Boy() {}
Boy.prototype = new Personal();

// 给子类添加原型方法必须在替换原型之后
Boy.prototype.printSource = function() {
 console.log('printSource~');
};

4.创建 boys 实例时无法向父类的构造函数传参,也就是无法初始化 source属性。因此:只能创建实例之后再修改父类的属性。

const boys = new Boy();

// 只能创建实例之后再修改父类的属性
boys.source = 100;

apply()、call()方法的继承

了解下apply()、call()方法

1.apply()、call()的用法:

obj.call(thisObj, arg1, arg2, ...);
obj.apply(thisObj, [arg1, arg2, ...]);

obj是父级,thisObj是子级;第二个参数apply可以接收一个数组,而call只能是每项逐个接收。

2.apply和call 本来就是为了扩展函数的作用域而生的,换句话说就是为了改变this的指向存在的。

3.当一个object没有某种方法,但是其他的有,我们可以借助call和apply来用其他对象的方法来做操作,也可以传参数。

//eg:
function Personal(name, sex) {
   this.name = name;
   this.sex = sex;
   this.say = function (){
    alert('姓名:' + this.name + ';性别:' + this.sex)
   }
  }
  const per = new Personal('Allan', '男')
  per.say();
  
//apply()方法实现:
  function Girls(name, sex) {
   Personal.apply(this, [name, sex]);
   //Person.apply(this,arguments); //跟上句一样的效果,arguments 
   //Print.apply(this,arguments); //还可以实现继承多个父类,但是原型 prototype只能继承一个父类!!!切记
  }
  const girls1 = new Girls('Lucy', '女')
  girls1.say();
  
//call()实现:
  function Boy(name, sex) {
   Personal.call(this, name, sex);
  }
  const boys = new Boy('Barry', '男');
  boys.say() //

总结:

  1. prototype可以动态的给对象增加属性和方法。
  2. 可以实现子类继承父类,拥有父类的属性和方法。
  3. call和apply的区别,在于参数的不同。
  4. call和apply,理解为在子类的运行环境中执行父类的方法和属性。
  5. call和apply可以实现一个子类继承多个父类,但是prototype只能有一个父类。

 以上所述是小编给大家介绍的js的继承方法小结详解整合,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对三水点靠木网站的支持!

Javascript 相关文章推荐
获取当前网页document.url location.href区别总结
May 10 Javascript
javascript实现焦点滚动图效果 具体方法
Jun 24 Javascript
struts2+jquery组合验证注册用户是否存在
Apr 30 Javascript
JavaScript bold方法入门实例(把指定文字显示为粗体)
Oct 17 Javascript
AngularJs $parse、$eval和$observe、$watch详解
Sep 21 Javascript
简单实现js浮动框
Dec 13 Javascript
Js apply方法详解
Feb 16 Javascript
微信小程序上滑加载下拉刷新(onscrollLower)分批加载数据(一)
May 11 Javascript
Angular4开发解决跨域问题详解
Aug 28 Javascript
微信小程序template模板实例详解
Oct 27 Javascript
js消除图片小游戏代码
Dec 11 Javascript
vue 解决兄弟组件、跨组件深层次的通信操作
Jul 27 Javascript
详解JavaScript的内存空间、赋值和深浅拷贝
Apr 17 #Javascript
Vue源码探究之虚拟节点的实现
Apr 17 #Javascript
ES6知识点整理之数组解构和字符串解构的应用示例
Apr 17 #Javascript
ES6知识点整理之对象解构赋值应用示例
Apr 17 #Javascript
ES6知识点整理之函数对象参数默认值及其解构应用示例
Apr 17 #Javascript
仿vue-cli搭建属于自己的脚手架的方法步骤
Apr 17 #Javascript
一篇文章,教你学会Vue CLI 插件开发
Apr 17 #Javascript
You might like
使用php来实现网络服务
2009/09/15 PHP
php中可能用来加密字符串的函数[base64_encode、urlencode、sha1]
2012/01/16 PHP
使用phpQuery采集网页的方法
2013/11/13 PHP
分享PHP源码批量抓取远程网页图片并保存到本地的实现方法
2015/12/01 PHP
PHP is_array() 检测变量是否是数组的实现方法
2016/06/13 PHP
利用php + Laravel如何实现部署自动化详解
2017/10/11 PHP
php使用redis的几种常见操作方式和用法示例
2020/02/20 PHP
php设计模式之观察者模式实例详解【星际争霸游戏案例】
2020/03/30 PHP
Add a Table to a Word Document
2007/06/15 Javascript
js字符串转换成数字与数字转换成字符串的实现方法
2014/01/08 Javascript
javascript版的in_array函数(判断数组中是否存在特定值)
2014/05/09 Javascript
jQuery实现模拟marquee标签效果
2015/07/14 Javascript
javascript比较两个日期相差天数的方法
2015/07/24 Javascript
JS+CSS实现简单滑动门(滑动菜单)效果
2015/09/19 Javascript
jQuery实现立体式数字动态增加(animate方法)
2016/12/21 Javascript
微信小程序中进行地图导航功能的实现方法
2018/06/29 Javascript
微信小程序实现pdf、word等格式文件上传的方法
2019/09/10 Javascript
mpvue实现左侧导航与右侧内容的联动
2019/10/21 Javascript
es6中使用map简化复杂条件判断操作实例详解
2020/02/19 Javascript
完美解决vue 中多个echarts图表自适应的问题
2020/07/19 Javascript
详细解读Python中的__init__()方法
2015/05/02 Python
使用Python3 编写简单信用卡管理程序
2016/12/21 Python
TensorFlow安装及jupyter notebook配置方法
2017/09/08 Python
Python向MySQL批量插数据的实例讲解
2018/03/31 Python
使用Numpy读取CSV文件,并进行行列删除的操作方法
2018/07/04 Python
详解Python中的type和object
2018/08/15 Python
python函数与方法的区别总结
2019/06/23 Python
Pytorch之Variable的用法
2019/12/31 Python
20行代码教你用python给证件照换底色的方法示例
2021/02/05 Python
HTML5新增的8类INPUT输入类型介绍
2015/07/06 HTML / CSS
Fairyseason:为个人和批发商提供女装和配件
2017/03/01 全球购物
中国汽车租赁行业头部企业:一嗨租车
2019/05/16 全球购物
单位接收函格式
2015/01/30 职场文书
保护环境建议书作文500字
2015/09/14 职场文书
Python中22个万用公式的小结
2021/07/21 Python
Tomcat配置访问日志和线程数
2022/05/06 Servers