前端基础框架学习让前端飞

生命周期函数与钩子函数 - 详解

2017-05-07  本文已影响169人  不洗头的野人

本文介绍

本文主要讲解在JavaScript中生命周期函数和钩子函数的实现,以及其原理。

可以说现在前端主流的框架都离不开生命周期函数,关于生命周期函数钩子函数,之前我经常看到有人将它们混为一个概念。其实还是有点区别的,可以说生命周期函数可能会包含着钩子函数,但也可能不包含,所以不是一个概念。下面例子会有助于你深刻理解这一理念。

其中JavaScript中的生命周期函数的实现,会跟其它语言有点不一样,这个得靠自己体会了,本文只是一个牵引。

说到生命周期函数,其实还涉及到一种设计模式 - 模板方法模式,但是本文不讨论,因为不会影响你对生命周期的理解。

本文代码风格: ES5

内容

生命周期

首先,来看下面代码:

// 模拟一个动物类
function Animal() {

}

// 由于每个动物都会拥有该生命周期,所以写在prototype上
Animal.prototype = {
  constructor: Animal,
  // 假设这4步骤就是一个动物生命中所经历的时期
  step1: function() {
    console.log('幼年');
  },
  step2: function() {
    console.log('少年');
  },
  step3: function() {
    console.log('中年');
  },
  step4: function() {
    console.log('老年');
  },
  // 当执行该方法时,就让生命周期按顺序来进行
  init: function() {
    this.step1();
    this.step2();
    this.step3();
    this.step4();
  }
}
// 创建动物
var dog = new Animal();
// 开启生命篇章
dog.init();

控制台打印如下:

控制台打印

但是,假如你是那种很有个性的人,觉得用幼年、少年、中年、老年来形容自己太枯燥了,你想改写人生,重新绘制自己生命的蓝图,那也是可以的,方法如下:

// 创建属于自己的人群
function ShaMaTe() {
    
}
// 继承自Animal
ShaMaTe.prototype = new Animal();
// 指定构造器,对原型链不了解的同学忽略这句即可
ShaMaTe.prototype.constructor = ShaMaTe;
// 重写方法
ShaMaTe.prototype.step1 = function() {
  console.log('*﹏拗哖〆…');
}
ShaMaTe.prototype.step2 = function() {
  console.log('尐哖');
}
ShaMaTe.prototype.step3 = function() {
  console.log('筗哖');
}
ShaMaTe.prototype.step4 = function() {
  console.log('荖哖');
}

var me = new ShaMaTe()
// 开启人生
me.init()

你发现一个不一样的人生,打印如下:

![控制台打印]](http:https://img.haomeiwen.com/i1486247/a2611126c669f227.jpeg?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)

好了,生命周期函数讲完了,这就是生命周期函数:

  1. 按顺序进行
  2. 可以改写函数,但函数还是按顺序进行

钩子方法

看完生命周期函数的例子,不知你有没察觉到该例子的缺点没有。那就是:在上面例子中,如果一个动物,假如它在幼年时期就死了,但它还是会进行后面的函数顺序。

因此在这里,我们要引入钩子方法

通过钩子函数返回值,来判断,来判断人生还有没必要再进行下去:

// 拿第一份代码中的Animal为例
Animal.prototype = {
  // 省略代码...
  
  // 我们只需要对init方法进行处理,其他保持不变
  init: function() {
    // 在这里,我作一种假设,仅为举例,具体的得按需求来
    // 动物在幼年时期是最容易死亡了,可能会被其它动物吃掉
    // 因此在幼年到少年期间,添加一个钩子函数,通过其返回值判断是否继续执行
    this.step1();
    if (this.dieInBabyhood()) {
        return
        // 后面的不再执行
    }
    this.step2();
    this.step3();
    this.step4();
  },
  // 然后给钩子函数一个默认返回值,默认为false(不死)
  this.dieInBabyhood: function () {
    return false;
  }
}

// 创建动物对象
var dog = new Animal();
// 重写钩子函数
dog.dieInBabyhood = function () {
    return true;
}
// 开启生命周期
dog.init();

打印如下:可怜的小狗只走到了幼年

![控制台打印]](http:https://img.haomeiwen.com/i1486247/80925c080705c2d8.jpeg?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)

其实还有一种需求就是:在生命周期中,仅仅跳过了某时期,下面的依然还要进行,这种需求实现如下:

Animal.prototype = {
  // 省略代码...
  
  init: function() {
    this.step1();
    // 拿仅跳过step2为例
    if (!this.isCrossStep2()) {
      this.step2();
    }
    // 后面依然执行
    this.step3();
    this.step4();
  }

总结

  1. 生命周期函数包含钩子函数
  2. 生命周期函数可以重写
  3. 通过重写钩子函数可以决定是否进行某一步操作
上一篇下一篇

猜你喜欢

热点阅读