leetcode

节流和防抖

const debounce = (fn, time) => {
    let timer
    return () => {
        if(timer){
            clearTimeout(timer)
        }
        timer = setTime(fn, time)
    }
}
 
const throttle = (fn, time) => {
    let prev = 0
    return () => {
        const now = Date.now()
        if(now - prev >= time){
            fn()
            prev = now
        }
    }
}
//debounce.js
 
/**
 * @param {*} fn 要执行的函数
 * @param {*} delay 延迟时间
 * @param {*} immediate 是否立即执行
 * @returns 
 */
function debounce(fn, delay, immediate = false) {
  // 1.定义一个定时器, 保存上一次的定时器
  let timer = null;
  let isInvoke = false; //记录立即执行是否已执行过
 
  // 2.真正执行的函数
  const _debounce = function (...args) {
    // 取消上一次的定时器
    if (timer) clearTimeout(timer);
 
    // 判断是否需要立即执行
    if (immediate && !isInvoke) {
      fn.apply(this, args);
      isInvoke = true;
    } else {
      // 延迟执行
      timer = setTimeout(() => {
        // 外部传入的真正要执行的函数
        fn.apply(this, args);
 
        //没有这个步骤时,只有第一次输入是立即执行,即使后面延迟执行后再输入也是延迟执行;
        // 有这个步骤时,第一次输入时立即执行,后面延迟执行后再输入也会有立即执行
        isInvoke = false
        timer = null
      }, delay);
    }
  };
 
  return _debounce;
}

函数柯理化

class转es5

手写instanceof

function myInstanceof(source, ctor) {
  /** 判断非引用类型 */
  if (!["function", "object"].includes(typeof source) || source === null) return false
 
  /** 查找原型链 */
  let proto = Object.getPrototypeOf(source)
  while (true) {
    if (proto === null) return false
    if (proto === ctor.prototype) return true
    proto = Object.getPrototypeOf(proto)
  }
}

手写call、bind

Function.prototype.myCall = function (ctx, ...args) {
  // 参数归一化
  ctx = ctx === undefined || ctx === null ? globalThis : Object(ctx)
 
  // 拿到要执行的函数
  const fn = this
 
  // 绑定函数到ctx,(优化:不能被遍历到)
  const key = Symbol("function_call")
  Object.defineProperty(ctx, key, {
    value: fn,
    enumerable: false,
  })
 
  // 执行函数并返回对应的结果
  const result = ctx[key](...args)
  delete ctx[key]
  return result
}
 
function test(a, b) {
  console.log(this, a, b, this.name)
  return a + b
}
 
console.log(test.myCall({ name: "tttt" }, 1, 3))
 
Function.prototype.myBind = function (ctx, ...args) {
  // 要执行的函数
  const fn = this
 
  return function A(...rest) {
    // 如果是 new 调用的,保留new的行为
    if (Object.getPrototypeOf(this) === A.prototype) {
      // 或者 this instanceof A
      return new fn(...args, ...rest)
    }
 
    // 执行函数并返回结果
    return fn.apply(ctx, [...args, ...rest])
  }
}
 
function test(a, b, c, d) {
  console.log(this, a, b, c, d)
  return a + b
}
 
const newFn = test.myBind({ name: "aa" }, 1, 2)
console.log(newFn(3, 4))
console.log(new newFn(3, 4))
 

手写深拷贝