← 返回目录

第 3 卷

第 3 / 8 卷日期:

71try { 72const result = onRejected(this.reason);

73result instanceof MyPromise ? result.then(resolve, reject) : resolve(result);

74} catch (error) {
75reject(error);
76}
77}, 0);
78}

79

80//处理等待状态(异步操作未完成时,缓存回调函数)
81if (this.status === PENDING) {
82this.onFulfilledCallbacks.push(() => {
83setTimeout(() => {

总结

1.new:创建新对象、绑定this、执行构造函数、判断返回值
2.call/apply:临时挂载函数、绑定this、立即执行、清理环境,区别仅在参数形式
3.bind:返回绑定this的新函数、支持柯里化、兼容new调用、维护原型链
  1. 简易Promise:维护三种不可逆转状态、执行器立即执行、 then 方法支持异步和链式调用、实现

值的穿透

六、手写防抖函数(debounce)

核心原理

  1. 防抖的核心是“延迟执行”:当函数被频繁触发时,只在最后一次触发后,等待指定时间再执行函

数

  1. 每次触发函数时,都清除之前设置的定时器,重新计时,避免函数多次执行
  2. 支持“立即执行”可选参数:开启后,第一次触发时立即执行函数,后续触发则重新延迟
  3. 支持“取消防抖”功能:可手动取消尚未执行的延迟函数

实现代码

Code block

1function debounce(fn, delay, immediate = false) { 2let timer = null; // 存储定时器ID

8 9// 每次触发都清除之前的定时器,重新计时

10if (timer) clearTimeout(timer);

11 12// 处理立即执行逻辑

13if (immediate && !isExecuted) { 14fn.apply(_this, args);

15isExecuted = true; //执行后标记为已执行
16} else {
17//延迟执行逻辑
18timer = setTimeout(() => {
19fn.apply(_this, args);
20isExecuted = false; //延迟执行后重置标记,允许下次立即执行
21timer = null; //执行完毕清空定时器
22}, delay);
23}
24};

25 26// 取消防抖:手动清除定时器,重置状态

27debounced.cancel = function() {

28if (timer) clearTimeout(timer);
29timer = null;
30isExecuted = false;
31};

32 33return debounced;

34} 35

36// 测试示例 37function handleInput(value) {

38console.log(`输入内容:${value}`);

39} 40

41// 1. 普通防抖(延迟500ms执行)

42const debouncedInput = debounce(handleInput, 500);
43//模拟频繁输入(仅最后一次输入后500ms执行)
44debouncedInput('a');
45debouncedInput('ab');
46debouncedInput('abc'); // 500ms后输出:输入内容:abc
48// 2.立即执行防抖(第一次输入立即执行,后续输入延迟)
49const immediateDebounce = debounce(handleInput, 500, true);
55const cancelableDebounce = debounce(handleInput, 1000);
56cancelableDebounce('需要取消');
57cancelableDebounce.cancel(); //手动取消,函数不会执行

58

七、手写节流函数(throttle)

核心原理

  1. 节流的核心是“控制执行频率”:当函数被频繁触发时,保证在指定时间内只执行一次函数
  2. 两种实现思路:
  • 时间戳法:第一次触发立即执行,后续触发时判断当前时间与上次执行时间的差值,大于等于延

迟则执行

  • 定时器法:第一次触发延迟执行,后续触发时若定时器存在则不执行,执行后清空定时器
  1. 合并两种思路,实现“第一次立即执行+后续固定频率执行”的完整节流效果
  2. 支持“取消节流”功能:手动取消尚未执行的延迟函数

实现代码

Code block

1function throttle(fn, interval) { 2let lastTime = 0; // 存储上次执行的时间戳

3let timer = null; // 存储定时器ID 4

5// 节流核心函数 6const throttled = function(...args) {

7const _this = this;

8const now = Date.now(); // 当前时间戳 9

10// 1.时间戳法:判断当前时间与上次执行时间的差值是否大于等于间隔
11if (now - lastTime >= interval) {
12//清除可能存在的定时器(避免时间戳和定时器双重执行)
13if (timer) {
14clearTimeout(timer);
15timer = null;
17//执行函数,更新上次执行时间
18fn.apply(_this, args);
全站分卷索引 · 8 卷
  1. 1第 1 卷
  2. 2第 2 卷
  3. 3第 3 卷
  4. 4第 4 卷
  5. 5第 5 卷
  6. 6第 6 卷
  7. 7第 7 卷
  8. 8第 8 卷