当前位置: 首页 > news >正文

电商网络推广免费网站seo优化

电商网络推广,免费网站seo优化,网页版qq农场,做网站 源代码摘要 在React中,如果涉及到了多次setState,组件render几次。setState是同步的还是异步的。这是一个很常见的面试题。 而本篇文章,就是主要实现React中,对于这部分的性能优化,我们称之为批处理。例如当我有下面的JSX。…

摘要

在React中,如果涉及到了多次setState,组件render几次。setState是同步的还是异步的。这是一个很常见的面试题。

而本篇文章,就是主要实现React中,对于这部分的性能优化,我们称之为批处理。例如当我有下面的JSX。

const root = document.querySelector('#root');function App() {const [num, setNum] = useState(0)const click1 = () => {setNum(num + 1)setNum(num + 2)setNum(num + 3)}return jsx("div", {onClick: click1,children: num});
}ReactDOM.createRoot(root).render(<App />)

对于当前的点击事件来说,只有最后的setNum(num + 3)是有效的。

但是在我们之前的实现中,对于这种连续三次setState,我们的代码就要处理三次,就要经过三次beginWork,completeWork,commitWork。

那我们能不能实现出一种方式,对于这种多次setState,最终之做最后一次处理。

1.修改update相关逻辑

目前,在我们的代码里,能够让组件更新的方式,就是通过setState,触发更新。而updateQueue就是用来保存更新的内容。

function enqueueUpdate(updateQueue, update) {updateQueue.shared.pending = update
}

之前,在enqueueUpdate方法里,我们是直接进行赋值的。这没什么问题,因为之前每次赋值之后都会更新一下。

但是现在我们希望,最后只更新一次的话。我们就需要一个数据结构,可以保存多次更新的内容。这里使用的是链表结构,但在真正的React源码中,使用的是环形链表。

function enqueueUpdate(updateQueue, update) {// updateQueue.shared.pending = updatelet pending = updateQueue.shared.pending;if(pending === null) {updateQueue.shared.pending = update}else{while(pending.next != null) {pending = pending.next;}pending.next = updatepending = pending.next;}
}

OK,修改完之后,我们调用了三次setState,那么updateQueue中保存的应该是一个链表了。

在之前的processUpdateQueue方法里,也是直接更新就完了。但是现在updateQueue的结构发生了变化,所以对于processUpdateQueue,更新逻辑也要改变。

function processUpdateQueue(baseState, pendingUpdate) {const result = {memoizedState: baseState}if(pendingUpdate.next === undefined) {const action = pendingUpdate.action;//setState(() => {}) 传入方法if(typeof action === 'function'){result.memoizedState = action(baseState);}else {//setState()result.memoizedState = action;}return result}while(pendingUpdate != null) {const action = pendingUpdate.action;//setState(() => {}) 传入方法if(typeof action === 'function'){baseState = action(baseState);}else {//setState()baseState = action;}pendingUpdate = pendingUpdate.next;}result.memoizedState = baseState;return result;
}

我们需要遍历pending,将所有的更新内容返回。

2.修改workLoop循环

我们想一下,之前触发更新后,执行的机制是什么样子的。

  1. 更新updateQueue
  2. 拿到更新的updateQueue,挂载Hook上
  3. 执行workLoop

也就是说,每次workLoop都只能拿到当前更新的内容。
如果我希望在第一次workLoop就可以拿到所有的更新内容,并且取消后面的workLoop。

有什么方法呢?微任务!!!!

我们可以将执行workLoop的过程放在微任务里,这样执行workLoop的时候,updateQueue的链表已经生成。

同时我们用一个标志位,取消后面的workLoop执行。
当workLoop执行完成后,再将标志位置反。

let isFinished = false;
export function syncWorkLoop(root,hostRootFilber) {if(isFinished) {return;}Promise.resolve(null).then(() => {wookLoop(root,hostRootFilber);})isFinished = true;`在这里插入代码片`
}
const wookLoop = (root,hostRootFilber) => {//其他代码。。。。。isFinished = false;
}

3.修改filberHook

最后,我们只要在filberHook中触发的逻辑里,替换workLoop即可:

function disaptchState(filber, hook, action) {const update = createUpdate(action);enqueueUpdate(hook.updateQueue, update);workUpdateHook = hook;syncWorkLoop(filber.return.stateNode);
}

通过这种方式,当我执行多次setState,最终只会render一次。

http://www.ds6.com.cn/news/95629.html

相关文章:

  • 织梦做企业网站seo上海优化
  • 做网站前端后台新站优化案例
  • 有什么网站可以做投票功能服务外包公司
  • 网站怎么做微博认证推广赚钱的平台
  • 佳匠网站建设株洲专业seo优化
  • 八年级信息上册如何做网站5118和百度指数
  • 北京专业做网站公司哪家好线上广告投放渠道
  • 网站设计的毕业论文题目有哪些最新新闻热点事件2023
  • 百度seo站长工具厦门网站搜索引擎优化
  • 做网站和网页的目的和作用是什么永久免费的培训学校管理软件
  • wordpress 改变网页鼓楼网站seo搜索引擎优化
  • 网站建设和空间搜狗seo培训
  • 好看的个人网站主页seo网站内部优化方案
  • 茶山东莞网站建设seo和sem是什么意思
  • 做网站的用什么主机好谷歌seo网站排名优化
  • 编程开发泽成seo网站排名
  • 影视在YouTube网站上做收益难吗查关键词的排名工具
  • 做国外网站用国内服务器如何查看百度指数
  • 学校网站前置审批交易链接
  • 音乐网站开发结语付费恶意点击软件
  • 专业手机网站建设推荐搜狗收录入口
  • 苏州城乡建设局的网站淘宝权重查询入口
  • 网站制作网站建设需要多少钱营销型网站建设要点
  • 农家乐网站开发项目背景国外引流推广平台
  • 网站管理建设工作seo推广优势
  • 招标公司网站建设方案北京网站优化经理
  • 驻马店市旅游网站建设深圳广告策划公司
  • 网站防恶意注册环球军事网
  • 开福区网站建设中网络整合营销
  • 杭州响应式网站制作免费网站在线客服软件