00:00
上节课我们写完了reactdu的一个数据共享版啊,也就是说这些组件都可以随便的去中去获取这个数据。啊,这里形成了笔记给大家看一下啊。还是在我们那个目录下这个笔记里面,诶在这里,这是我们的一个数据共享版。那我们写这个数据共享版的这个整个过程就是先定义了一个P组件啊,我边说这个笔记边给大家看,我们在这里定义了一个P的一个组件,对不对。然后。和count组件。通过这个。Re,啊,去共享这个数据啊,就这两组间要通,通过这个re,共享的数据嘛。然后我们先写的什么呢?是为这个person组件去编写了啊,我们这个Du相关的,比如说这个reducer啊,还有这个action啊。最后呢,要在这个抗里面配置一下person组件需要的一些常量。接下来就是percent reducer和count的reducer,哎,都要使用这个进行合并。
01:04
这个是在我们这个套里面,因为现在我们要让套去,就说处理多个reducer,那我们只能传入一个总的一个reducer,然后使用这个方法进行合并啊,所以我们接收到这个参数就是我们。就是说redu中存的总对象,哎,我们其实在这里定义了redu,它存的总的这个对象,那我们后面在使用的时候,一定按按照我们存的这个键去使用啊,存在这个K去使用,不要使用错了,这也是最后一个,就是我们在容器组,容器组件中取出来这个状态使用的时候,比如说我们这个容器组件取出来这个状态使用的时候,你要按照指定的这个K获取,那我们存的是I这个和就取这个和取这存的是这个人,人就取这个人事啊,那就是我们在这里定义的这个一定不要乱啊。那这个我们就先关了,把这个呃,文件内容给给复制一下啊。
02:02
接下来我们建一个零七啊,这个复制完了建一个零七,因为这个给大家保留一个版本。零七作为我们最终优化的一个版本。我们叫,嗯,最终版吧,Fi的NL。啊零七。接下来诶,我们还是得进到这个目录,把刚才删掉的这个依赖给安装一下啊,CD加点杠上一层零七。嗯,不要太不见不全啊。然后加。不写也可以,好像里面装着,接着我们来看一个问题啊。什么问题呢?之前我们在写这个person,这个reducer的时候。大家想一想,哎,看代码说吧,就是我们在写这个。Person这个reducer的时候。在这里。
03:01
看看这里我们要把一个数据给合并到这个数组里面,对吧,然后当时我给大家说了,不要不要使用那个那个Una,或者使用这个push,我们使用这种方式,那为什么不使用这个on shift呢?那这里我们来使用一下,那这个我先注释。我们使用这个啊UN shift将。这个date。加到这个数字的前面来,最后我们来return。这个PI state,哎,因为这个UN shiftft呢,它是呃,在这个数组的前面去增加了一条这个数据啊,我们直接把这来看一看这个效果啊。嗯,还没有运行是吧,因为之前关过一次。这里先启动一下。Yeah start。启动之后我们在这里,哎,让它刷新。好,我们改的是谁,是这个P组件是吧,现在我来添加一个人,添加一个A,然后年龄是一来添加是不是没有反应,对啊,这里看这里没有增加,下面人也没增加对吧,对吧,那好,那接下来我们想一个问题,那。
04:13
怎么就没有增加呢?大家是不是对这个产生了一个怀疑,这个UN。不可能失效吧,啊,我们给大家打印一下,你看看这个结果,哎,就是看一下它,我。O log啊,来输出一下。便宜。保存。好刷新一下把这个清了,那现在我添加还是添加个啊AA,然后00:11添加,这是我们输出的,你可以已经看到这个数组里面已经有了两个元素,对吧,那第一个就是。我们。原来的。啊,就是说。这个第一个这个是我们。这个新加的对吧,那第二个这个001是我们初始化的这个对不对,那说明我们新加的这个,比如说AA1,它已经加到了这个第一个。
05:01
哎,也就是说这个按shift肯定是生效的,它的数据也改变了,哎最后我们也返回了,但为什么就是不生效呢。啊,你使用push也是一样的一个结果啊。那这个我给大家说一下啊,这个是因为我们的这个reducer,它是一个纯函数,对,它是一个纯函数,哎,这时候我们就引出了一个新概念纯函数对吧。来给大家看一下,我们写了一个笔记啊。纯函数。那什么是纯函数呢?纯函数啊,其实就是一类啊,特殊的一个函数。这里面给大家写啊,把这个定义写一写定义啊,纯函数就是。一类特殊的函数啊啊,遵循。以下规则。哎,遵循这些规则,那我们接着来看一看啊。首先你要明白,其实纯函数它也就是函数对吧,只不过它。
06:04
有一定的规则,那先看第一个规则。也就是说,我们。就是说返回的。始终,它始终返回相同的一个值,哎,这是传中第一个规则,就是无论我们什么时候调用,都会返回相同的一个值。清楚吧,啊,比如我们的这个math.cos它无论什么时候调用都是返回的,是固定的一个值。我们。直接。然后不写代码了,我直接在这给大家看啊好。比如说这个函数,你无论什么时候调用,你哪怕你你过几个月啊,你过几年你再调用它,结果还是返回的这个一。清楚了吧,啊,无论什么时候调用返回的都是同样的,这是第一个,那比如我们还我还给大家列举了一个不是的,比如这个math random,它就不是纯函数。来,在这里我们继续来看11看一下啊。来,你现在调它是这个值,你现在调它是这个值,对吧,每一次调的结果都不一样,这个就不是从函数,这就是它第一个概念,哎,当然这里我们写的是两个系统已经有的一个函数,那如果我们自己去写呢?啊。
07:08
也很能也能轻松的写出不是纯函数的一个值。清楚了吧,嗯。这是第一点啊,就是说它要始终返回相同的值。注意这个返回。相同的值。是什么意思啊,就是说无论我们什么,就说在参数固定的情况下,无论我们什么时候调用。它返回相同的值啊,我给大家写一写吧,在这下面写吧。比如说something。我来写个DEMO啊。好,这个DEMO呢?他需要接收一个A,然后我这个A。A,或者我这个A加一来,现在我调DEMO,然后我传入一个一。嗯,Lo一下这个结果吧,来。Olo一下这个结果。
08:03
来,我们在这里来刷新。是不是二,你看我再刷新它是不是还是二,也就是说。我无论什么时候调用这个DEMO,它都是二,这是反过来相同值对不对。哎,那我们的这个DEMO就是函数这个纯函数来,那比如我这次传入了这个三,我现在刷新啊。第一个返回的是二,第二个返回的是四,对吧?啊。但是它呢,它还是损函数,因为它返回的值没有变,那你说了啊,这两个值不一样,这是因为我们传的参数不一样,你不要把这个概念给搞混了,我们的第一个定义就是说是它始终返回相同的值。清楚了吧,啊,如果你还不太低看,我们第二个,也就是返回的结果只依赖于它的参数。这点一定要搞清楚啊,不是说它的值就固定了是一,就永远是是一,它要取决于我们的这个船的这个参数才行。明白了吗?只不过我们在参数一定的情况下啊。来。
09:00
就是说我们参数一定的情况下,哎,我们什么时候调用它的结果才是一样的,明白了吗?啊,就是像我们的这个例子对吧?啊。好,这是第一点来看,我们第二点返回的结果只依赖于它的参数,不改变参数的值,不使用外部变量。啊,这个就比较好理解了是吧?啊,那比如我们的这个函数啊。来写写啊。好,现在呢,我们这个函数。比如说它让A等于等于了二。啊,A等于二,这是不是我们把原来参数的值给改变了,那假如我们这里调用我们传入了A等于一,A等于一,是不是结果这个A等一在这里变成了A等于二啊,我们是不是改变了参数的值就不符合这一点?啊,就不是一个纯函数了,这就不是一个纯函数,好接着看一下不使用外部的变量,那假如我们外部还有一个,哎,比如说B等于三,B等于三,然后我们返回的结果,结果是A加B。这个也不是纯函数。
10:02
因为你使用了外部的变量。清楚了吧,你看你使用的外部的这个B这个变量,我们纯函数,你必须所有使用的变量都是函数自己内部定义的,你这个B如果是你函数内部的没问题啊,当然你还不能去修改这个参数啊,我们这个是有算函数,我们这个B是自己内部定义的,明白了吧。啊,这是第二点。我们先把那个存函数的规则给理解完,接着再看一看我们的硫算啊,还有一点就是说我们存函数你在执行过程中不能有任何副作用,那什么叫副作用,比如说你修改了外部的一个变量啊,那你你都不能使用,你这边修改肯定就有问题啊,对不对?好,但是这个我说的这个修改了外部的变量是存在一种。什么样的情况呢,就存在一个比较复杂的一个情况啊,比如说是比如。参数是一个地址的引用。哎。
11:00
好,那就这么说吧啊。这是什么意思呢?比如我们传的是一个对象,因为我们知道对象是一个地址的引用,假如我们在里面修改了这个外部的变量也会引起作用,那其实已经不符合这这一条规则了,对吧,你改变了参数的这个值啊,这两个其实也是有点类似的啊,啊,那怎么怎么说呢。嗯。看看啊。来我们来写一个啊,比如说是一个OBD。好,最后我们来。Return o BG,哎,我这里面我就不做其他运算了啊,接下来我们来传一个OBG,传一个谁A等于一啊BO2对吧,我现在传了一个谁传了一个对象是不是好,我在这里来定一下啊来比如说。来O等于这么一个对象,我把这个对象传到这个函数里面对吧,这个我定义的这个对象呢,作为一个参数传给这个函数对不对,但是这个函数里面他干了一件什么事,他把这个OBG,比如说点A,它给改了对不对,改成了三好,那无论从哪个看,它都是不对的,比如说按我们第二条规则,它修改了外部的。
12:12
参数是不是因为你原来的OBD是A点一,然后这边修改了对吧?啊。注意啊,这个我们传的是什么?传的是对象,因为你如果传的是一个对象的话,我们传的实际上是地址的一个引用,也就是说我们是这么改了之后再对,就是说外部的这个O都发生了这个变化,明白吗?我们。比如我们现在打一下oo.log你看一下啊。蓝刷新。是不是O变成了A变成了三,我们这里还定义的A是一,B是二,但是这里去打印,打印这个就是这里执行了这个函数,这个函数里面干了什么,函数里面把把这个OBG的这个点删改了,哎,你可能有疑问,那我这里是定的O,这里是OBG啊。传,我只不过是把这个O传过去,注意啊,这不是直传的,是引用传递啊,你传的是他们在地址中的一个地址。明白了吧,所以你这边修改了,就对原原来的数据产生的影响,这个O也变了啊,所以这个就更不是纯函数了,甚至都不不符合这个,首先第一个你改变的参数值,第二个你修改了完变量产生了一些副作用,那你产生的这个副作用什么副作用就是。
13:16
外部变量值发生了改变,我原来外部变量是A1B2,经过你的这个函数一定要用好了,哎,我变成了A3B2,这是不是一个副作用,你看看对不对,这是我们这个第二条,那还有产生一些副作用的情况下,比如说你发起的网络请求。或者说你啊,你调用了这些到我们的API,修改了页面的一个一些元素,那是不是也是副作用。对吧,甚至连康都不行。啊,这是纯函数的三个规则。好,当然这个,呃,为了让大家更好的也写的有点长,那总结一点的话就是。总结一点就是说。哎,总结三点吧,第一个你不能去使用外部的一个变量,第二个你不能改参数啊,你不能改参数的值,那你就呃,就别说这种形式了啊。
14:04
好,第三个就是说。不能产生副作用。还有最重要一点,哎,那也其实算到第一个里面啊,就是说。它返回的值始终是固定的一个值,哎,始终是相同的值,返回相同的值啊,不是固定的,就是在我们参数。同样的情况下啊,因为它的结果反馈的结果只依赖于参数嘛,在参数同样的情况下。哎,它只会返回相同值,不会返回其他值,比如你参数是一,它返回了一对吧,那永远掉,它就你都是参参数一返回一,那不可能说,呃,你参数一它返回了二,那这就不是了啊,当然你参数如果变了,比如说参数变成了五,它返回了五,哎,这个其实它还存万数,我们的结果一只依赖于参数对不对,而且没有改成参数值,一定要符合这些规则啊。嗯,接着啊,底下的这个我们先不看,先来说一说,把这个删了啊。先来说说我们的这个问题,为什么这里它就不执行了,你看看啊。
15:07
对不对,为什么我们这个它就不实行了,但是实际上数据是已经放到了这个里面啊,那为什么就不生效了,这是因为之前我也给大家强调过,我们的这个reducer它一定是一个纯函数,接着现在来回想一下我们存函数的定义,你看一看。我们是不是在这里去改写了这个参数的值,你看因为这个按shift,它是直接向元素组它操作的元素组,它是在元素组的前面去剖析了一个。剖析了一个这个啊,不是谱系,是上元素组的前面去添加了一个对象,对吧,添加这个元素。是不是啊?而且他一是改了这个参数,第二个我们这个。P,它是什么?它是一个数组对吧,数组呢。它也是一种比较特殊的参数,一种复杂的类型,我们传过来的也是一个地址中的一个引用,那这里我们对这个元素组进行了修改,其实也相当于修改了,哎,外部他们,呃,就是说这个地方传过来的一个数据,对吧,那不管从哪一条看。
16:11
它都不是一个纯函数,它都不存了,对吧。啊。那所以不能这么去写,对不对啊,甚至我们连康log都不是,那怎么解决这个问题呢?我们可以诶这么去做,因为我们这么去做的话,相当于去新生成了一个数组,并没有改变原来参数对不对,我们只是说哎,借用原来参数的,就是说原来传的这个参数的数据,然后我们自己新加了条,重新组成了一个新的一个数组。清楚了,假如我这个PI,我传的是这一个参数,我得到的这个结果必定啊,然后再假如我这个date是。呃,是其他的一个参数啊,比如说是这个一个。随便写一下,比如说是嗯二,然后是这个name,然后是这个。内是这个A是这个好,12好。
17:02
假如我的这个PI,哎,我们一开始初始的话是这个值,然后我的对我的date,哎,是这个值的话,我得到的这个结果必定。是这个相同的,明白了吧,无论我何时调,因为我的参数你看是固定的,然后我的结果也是固定的,这也是符合我们纯函数的第一条的一个定义。清楚了吧,啊好。嗯。在哪里写呢,写一下呢,写到这里面吧。C。啊,是纯函数啊。只有它符合这个存函数的时候,我们这个才会生效。清楚了吧,啊,那我们这里因为是新新建了一个数组,并没有对参数产生影响,也没有修改原参数,也没有呃什么,只是用了一下参数的数据,对不对?哎,所以我们这个是可以生效的,来看看效果啊。刷新啊,这就没问题了,对不对,这是我们之前给大家讲过,我们在操作这个的时候,你不要去使用,嗯。
18:11
不要使用啊,这个什么啊。Saved on。然后以及这个push等等的一类操作啊,因为这个这个这个reducer啊reducer我们这个函数是纯函数,在这里再给大家补充一遍,这点要记清楚啊,那我们这个无所谓,这个新生成的一个数组啊,我要标注上啊,这是新生成的数组。哎,这个就。先上传的速度啊。接着看,我们纯函数这么复杂,为什么还要用这个纯函数?第一个他靠谱,他不会产生不可预料的行为,也就是说我们什么时候去调用它,它的它的结果,它的返回值。哎,始终是相同的,非常非常的靠谱啊。也不会对外部产生的影响。啊,那我比如调用函数,你也不会对外部你的这些变量啊什么的结果产生影响,而且重函数的话更利于调试,还一一组合,一一并行开发,这都是重函数的一个优点。
19:10
啊,所以我们再去呃开发呃,就是说我们在自己写代码的时候,尽可能的去使用纯函数。啊,尽可能的就是说呃,少依赖于外部的一些变量啊,尽可能让自己的这个函数。啊,保持自己的一个独立的一个结构,比较方便我们去。哎,调试开发以及维护啊,以及这个并行的这个开发啊。而且这个最后大家强调redux中的reducer,它必须是一个纯函数,好,因为它靠谱对吧。那就是这节课的一个内容,给大家讲一下这个纯函数的一个定义,然后在下一小节呢,我们再对我们的代码进行一些优化,比如啊这些变量啊什么的呀。啊,因为我们之前写的像这些变量都。比较随意是吧,啊比较随意,那我们在下节课来进行优化,这些人的先到这里。
我来说两句