问题描述:

现在有个需求,现有一个列表table,里面的数据有启用的也有关闭的,switch组件会根据数据状态展示,同时进行排序,启用数据在前面,未启用的在后面.如图

然后现在需要操作,假如我将第四条数据'的撒管道施工'进行启用,调用启用接口,改变switch组件状态,并重新调用列表查询接口,理想效果,列表数据按启用排序,前三条应该是启用,其他情况是未启用.可实际结果如图

所操作的数据状态确实对了,排序也ok的,但是"第四条数据的switch组件状态没有更新",刷新页面之后,组件更改了.

也就是结果是,switch正确切换了,但是第二次回显还是保留了回显前的状态.代码

代码如下:

 {
title: '是否启用',
dataIndex: 'whetherUseing',
key: 'whetherUseing',
// width: 150,
render: (text, record, index) => {
if (text === 1) {
return (
<div
id={`${record.id}${index}${text}`}
// key={`${record.id}${index}${text}`}
>
<Switch
defaultChecked={true}
disabled={!access_enable}
onChange={(value) => startOrEnd(value, record)}
/>
</div>
);
} else {
return (
<p
id={`${record.id}${index}${text}`}
// key={`${record.id}${index}${text}`}
>
<Switch
defaultChecked={false}
disabled={!access_enable}
onChange={(value) => startOrEnd(value, record)}
/>
</p>
);
}
},
},

 产生现象的原因:

主要是react的diff算法导致的.diff算法在以下三种情况时会重新构建一个新的DOM树.

(1)当dom的种类发生变化时,比如div变成了p标签

   (2)当dom的结构发生变化时,比如由原来的父子结构变成了兄弟结构

   (3)当dom的key发生变化时,你可以为dom元素加上key属性,当(1)和(2)不满足时,可以属性发生变化也会导致重新构建dom树

那switch组件这边发生了什么呢?

启用前:switch组件的父元素是一个p标签,打开tab第五栏的开关之后,开关变成了打开状态.接下来就是问题所在,当重新调接口后,该数据确实变成了启用状态,排在了前面(正确),但是,table第四栏的数据是关闭状态,所以逻辑上仍然走else,所以swtich的父元素dom种类没变,dom结构也没变仍是p标签.所以swtich标签以及p标签并不会更新.所以保持了打开状态.其结果就是,明明数据变成了关闭,可switch标签仍是打开状态.简单来说就是.

主体:table的第四栏的swtich(并非是某条数据)    过程:关闭-----(手动打开,此处此时的数据状态仍为关闭,但是swtich的checked属性变成了true)----->>>打开---------(调用接口,数据更新,第四栏的数据更新了,变成了别的数据,而这条数据仍是关闭.switch开关保持原样,checked属性仍为true)------>>打开(更新了,但没完全更新)

解决方案:

给switch标签加上key属性,既然你数据变了,而我也希望你switch也跟着边,那我就把你的key和你的相关数据绑定.根据diff算法特性,只要你key变了,那就会重新渲染

代码:

  {
title: '是否启用',
dataIndex: 'whetherUseing',
key: 'whetherUseing',
// width: 150,
render: (text, record, index) => {
if (text === 1) {
return (
<div
id={`${record.id}${index}${text}`}
key={`${record.id}${index}${text}`}
>
<Switch
defaultChecked={true}
disabled={!access_enable}
onChange={(value) => startOrEnd(value, record)}
/>
</div>
);
} else {
return (
<p
id={`${record.id}${index}${text}`}
key={`${record.id}${index}${text}`}
>
<Switch
defaultChecked={false}
disabled={!access_enable}
onChange={(value) => startOrEnd(value, record)}
/>
</p>
);
}
},
},

主体:table的第四栏的swtich(并非是某条数据)    过程:关闭-----(手动打开,此处此时的数据状态仍为关闭,但是swtich的checked属性变成了true)----->>>打开---------(调用接口,数据更新,第四栏的数据更新了,变成了别的数据,而这条数据仍是关闭.在结构和标签类型都不变的情况下,key发生了变化,重新构建渲染)------>>关闭(重新构建一个p标签,并获得 defaultChecked={false} )

react的diff算法与antd中switch组件不更新问题的更多相关文章

  1. 深入理解React:diff 算法

    目录 序言 React 的核心思想 传统 diff 算法 React diff 两个假设 三个策略 diff 具体优化 tree diff component diff element diff 小结 ...

  2. React的Diff算法

    使用React或者RN开发APP如果不知道Diff算法的话简直是说不过去啊.毕竟"知其然,知其所以然"这句老话从远古喊到现代了. 以下内容基本是官网文章的一个总结.压缩.这次要谦虚 ...

  3. 个人对于React的Diff算法的一点疑问(待更新)

    本人对于Diff算法也并未做深入研究,只是大概的看过一些博文了解了些原理,但依然有了如下疑问 : 对于vdom所表示的对象中,若在该oldObj和newObj之间,发现一个元素节点所表示的子对象不见了 ...

  4. React的diff算法(译文)

    前言  此篇文章主要是因为在看Virtual DOM(虚拟DOM)的时候看到的主要讲的是实现Virtual Dom 的diff算法,原文地址:https://calendar.perfplanet.c ...

  5. react中虚拟dom的diff算法

    .state 数据 .jsx模板 .生成虚拟dom(虚拟DOM就是一个js对象,用它来描述真实DOM) ['div', {id:'abc'}, ['span', {}, 'hello world']] ...

  6. React——diff算法

    react的diff算法基于两个假设: 1.不同类型的元素会产生不同的树 2.通过设置key,开发者能够提示那些子组件是稳定的 diff算法 当比较两个树时,react首先会比较两个根节点,接下来具体 ...

  7. react性能调谐与diff算法

    一个页面其实就相当于是一颗dom树,里面有很多它的子节点,然后你每次去操作一个事件,它都会生成一个虚拟dom,它会跟上一个虚拟dom进行比对,这里运用的算法叫做diff算法,当它找到需要改变的组件的时 ...

  8. diff算法

    diff算法的作用计算出Virtual DOM中真正变化的部分,并只针对该部分进行原生DOM操作,而非重新渲染整个页面. 传统diff算法 通过循环递归对节点进行依次对比,算法复杂度达到 O(n^3) ...

  9. 虚拟dom?diff算法?key?Vue原理的核心三问?打包教你搞定。

    为什么需要虚拟DOM 先介绍浏览器加载一个HTML文件需要做哪些事,帮助我们理解为什么我们需要虚拟DOM.webkit引擎的处理流程,如下图所示: 所有浏览器的引擎工作流程都差不多,如上图大致分5步: ...

随机推荐

  1. N体模拟数据可视化 LightningChart®

    N体模拟数据可视化 LightningChart ​ N体模拟也许是目前最先进的数据可视化类型之一.事实上,我们现在谈论的不再是以商业为中心的传统数据的可视化,现在它甚至超越了比如振动分析等先进数据源 ...

  2. Swift-技巧(六)设置按钮状态并更改

    摘要 按钮是一个宝藏控件,可以在设置的时候就对不同的状态添加图片.文本,甚至更改背景.在不同的展示场景中更改到不同的状态显示就好.恰恰是如何更改状态着实让我懵了一阵,所以记录一下过程.如果没有兴趣了解 ...

  3. [loj2265]最长上升子序列

    以下内容参考2019年集训队论文<浅谈杨氏矩阵在信息学竞赛中的应用> 1.前置知识 杨表 标准杨表:一张网格图,满足以下条件-- 1.设其有$m$行.第$i$行有$a_{i}$个格子(格子 ...

  4. [loj6031]字符串

    为了方便,用$N=10^{5}$来描述复杂度 (对原串建立SAM)注意到$\sum|w|=qk\le N$,考虑对$q$和$k$的大小关系分类讨论: 1.若$q\le k$,即询问次数较少,将其与原串 ...

  5. [loj3333]混合物

    假设选择的调味瓶为$k_{1}<k_{2}<...<k_{s}$,即判定是否存在正有理数解$\{x_{1},x_{2},...,x_{s}\}$,满足$$(\sum_{i=1}^{s ...

  6. Qt Creator 源码学习笔记03,大型项目如何管理工程

    阅读本文大概需要 6 分钟 一个项目随着功能开发越来越多,项目必然越来越大,工程管理成本也越来越高,后期维护成本更高.如何更好的组织管理工程,是非常重要的 今天我们来学习下 Qt Creator 是如 ...

  7. 【SCOI2005】繁忙的都市

    Description 城市C是一个非常繁忙的大都市,城市中的道路十分的拥挤,于是市长决定对其中的道路进行改造.城市C的道路是这样分布的:城市中有n个交叉路口,有些交叉路口之间有道路相连,两个交叉路口 ...

  8. 洛谷 P5206 - [WC2019]数树(集合反演+NTT)

    洛谷题面传送门 神仙多项式+组合数学题,不过还是被我自己想出来了( 首先对于两棵树 \(E_1,E_2\) 而言,为它们填上 \(1\sim y\) 使其合法的方案数显然是 \(y\) 的 \(E_1 ...

  9. Environment Modules 简明教程

    Environment Modules 简明教程 1. Modules 简介 在 Linux 超算平台上,通常会安装有不同版本的多种编译器和其他软件等,如常用的编译器有 intel 和 gnu,常用的 ...

  10. composer设置阿里云镜像源

    composer设置阿里云镜像源 1. 首先把默认的源给禁用掉 composer config -g secure-http false 2. 再修改镜像源 这里我使用阿里的源 composer co ...