前端框架原理概览

14 天前(已编辑)
/ ,
11

前端框架原理概览

1. 前端框架原理

现代前端框架几乎都是基于描述自变量UI 视图之间的关系建立的,即“数据驱动视图”

UI=f(state)UI=f(state)

前端经过长时间的发展,对于 UI 的描述语言逐渐衍生出两种解决方案

  • JSX(代表框架:React):类 XML 语法的 ES 的语法糖
  • 模版语法(代表框架:Vue,Svelte)

2.前端框架分类的依据

对于公式 UI = f(state) 在“自变量与因变量”理论中,state 的本质是自变量,自变量通过直接或者间接(自变量导致因变量变化)的方式来改变 UI。“被改变的 UI”仅仅是”对宿主环境 UI 的描述“,并不是实际宿主环境的 UI。

所以,**UI = f(state) **可以进一步概括为两步:
  1. 根据自变量(state)变化来计算出 UI 的变化
  2. 根据 UI 的变化执行具体宿主环境的 API
至此我们可以根据**前端框架与自变量建立的对应关系的抽象层级**来划分前端框架
  • 元素级:Svelte
  • 组件级:Vue
  • 应用级:React

3. 细粒度更新

React 中定义因变量时候需要显式的指定出依赖项,而 VueMobx 不需要

// React
const y = useMemo(() => x * 2 + 1,[x]);
// Vue
const y = computed(() => x.value * 2 + 1);
// Mobx
const y = computed(() => x.data * 2 + 1);

在 Vue 和 Mobx 中使用的“能自动追踪依赖的技术”被称为“细粒度更新”,它同时是许多前端框架剪力“自变量变化到 UI 变化”的底层原理。

4.实现 React 中的一些 Hooks

此处不管是 effect.deps 还是 state 对应的 subs 都使用了 Set 利用了集合不会重复添加数据的特性,用细粒度更新实现的 hooks 不需要去显式的指出依赖

4.1 useState

function useState(value){
  // 订阅该state变化的effect
  const subs = new Set();

  const getter = () => {
    // 获取当前上下文的effect
    const effect = effectStack[effectStatck.length-1];
    if(effect){
      subscribe(effect,subs);
    }
    return value;
  }

  const setter = (nextValue) => {
    value = nextValue;

    // 通知所有订阅该state变化的effect执行
    for(const effect of [...subs]){
      effect.execute();
    }
  } 
  return [getter,setter];
}
function subscribe(effect,subs){
  subs.add(effect);
  // 依赖关系建立
  effects.deps.add(subs);
}

4.2 useEffect

const [count,setCount] = useState(0);

useEffect(() => {
  console.log('count is:',count());
})
setCount(2);

useEffect 实现的关键在于建立 useState 和 useEffect 之间的订阅关系

  1. 在 useEffect 回调中执行 useState 的 getter 时,该 Effect 会订阅该 state 的变化
  2. useState 的 setter 在执行时,会向所有订阅了该 state 变化的 effect 发布通知
const effect = {
  // 用于执行useEffect回调函数
  execute,
  // 保存该useEffect依赖的state对应的subs的集合
  deps: new Set()
}
function useEffect(callback){
  const execute = () => {
    // 重置依赖
    cleanup(effect);
    // 将当前effect推入栈顶
    effectStack.push(effect);

    try{
      // 执行回调
      callback();
    }finally{
      // effect出栈
      effectStatck.pop();
    }
  }

  const effect = {
    execute,
    deps: new Set();
  }

  execute(); // 自动收集依赖
}
function cleanup(effect){
  // 从该effect订阅的所有state对应subs移除该effect
  for(const subs of effect.deps){
    subs.delete(effect);
  }
  effect.deps.clear();
}

4.3 useMemo

function useMemo(callback){
  const [s,set] = useState();
  // 首次执行callback后,建立回调中state的订阅发布关系
  useEffect(() => set(callback()));
  return s;
}

4.4 VirtualDOM(虚拟 DOM)

又称 VDOM 是目前根据自变量变化计算出 UI 变化的一种主流技术

Vue 中使用模版语法来描述 UI,模版语法编译为 render 函数:

  1. render函数执行后返回“VNode 描述的 UI”,这一步骤中 Vue 中被称为 render
  2. 将变化前后“VNode 描述的 UI”进行对比,计算出 UI 中变化的部分,这一部分在 Vue 中被称为 patch

React 使用 JSX 来描述 UI,JSX 编译为 createElement 方法:

  1. createElement 方法执行后返回“React Elemet 描述的 UI”
  2. “将 React Eleme 描述的 UI”与变化前“Fiber Node 描述的 UI”进行比较,计算出 UI 变化的部分,同时生成本次更新“Fiber Node 描述的 UI”

5.React 实现原理

React 被称为应用级框架的原因在于--其每次更新流程都是从应用的根结点开始,遍历整个应用。同理,Vue 起始于组件,Svelte 起始于元素。

使用社交账号登录

  • Loading...
  • Loading...
  • Loading...
  • Loading...
  • Loading...