粉丝8.7万获赞13.8万

让 ai 一 次写一千行代码,里面有五个 bug, 怎么找出里面的五个 bug? 你 是不是蒙了?今天教你一招,让 bug 无处可藏!很多人让 ai 写代码,上来就说帮我写一个完整的登录系统, ai 很 听话,刷刷刷的帮你写了一千行代码,但是你一运行我错了,然后你盯着这一千行代码, bug 在 哪里也不知道。 ai 查来查去,问题越来越多,是表单的问题,是验证的问题,还是接口的问题,根本找不清楚 ai 写代码的最大的问题是什么,不知道自己错了,而且还特别自信的说,这次你运行一定不会再出问题了。最主要的是,代码越多, bug 藏的越深。 正确的做法是一次只做一件事情,不要说帮我写一个用户登录系统,要拆开说。第一步,先写登录表单的 u r、 e, 写完了跑一下,没问题了才进行下一步。第二步,再写一个表单验证的日期,写完测一下,没问题了,继续下一步。第三步,再写 api 调用,写完再测一下,最后一步 写错误处理,每一步写完就测,测完再进行下一步。这样做有什么好处呢? bug 出在哪里你立刻就知道,刚才还好好的,这一步坏了,那问题就出在这一步。不用一千行代码里大海捞针,很容易就知道问题出在哪里 了。所以小步快跑,步步验证,不要想一口吃成胖子,关注我,下期教你为什么一定要让 ai 解释他写的代码?

我要介绍的第三个工具就是 dfdf 命令,可以比较两个储物文件的差异,类似于我们进行 d 的开发,进行不同版本的一个比较。 下面让我们来看一下如何使用。假设我们有两种这样的数据,第一种 是一种 id, 第二种也是一种 id, 这两种 id 中有相同部分,也有不同部分。让我们来看一下,通过地图命令来把 第二个文件中相对第一个文件新增和删除的行找出来, 我再一个单剖,不如下准备了两个文件,一个叫地方一,一个叫地方二,我们看 看一下其中内容, 然后让我们用 dobe 对这两个文件进行比较,注意一下文件的顺序,我们是 fo, 一在前方,二在后。回车看一下数数结果, 还可以看到在输出结果中,基本上有几部分组成,一部分是像数字加字母加数字这样的, 其实这样的行呢,就代表是第一个文件的哪一行,然后是第二是一个字母,代表是先操作 d 呢,代表就是删除。 第二个数字呢,代表的是第二个文件中是哪行。二,第一就代表的是第一个文件中的第二行,相对于 第二个文件,第一行进行了删除,什么意思呢?大家可以看到在二第一下面有一个左键括号,就是小于号,后面是幺幺零幺零五。 看一下前面文件的例子中,第一个文件中是在第二行有幺幺零幺零五的,在第二个文件中第二行是没有幺幺零幺零五这个 id 的。 也就是说二代表是第一个文件的第二行, d 代表是在第二个文件中已经被闪除一代表是在第一个位就没有找到, 同样的道理,右肩好,这是大于号,实际上就是第二个文件中竞争的内容,在第一个 文件中没有找到。需要注意的是,大家在使用地服命令进行比较以前,需要对两个文件先进行排序,要不然比较的结果可能会是错误的。好,让我们先使用示好的命令对原文件进行排序, 然后再看一下比较的结果。 我们用杠 s 代表时排序过后的结果,同样对第二个文件也进行同样的排序操作, 然后对排序后的结果再进行比较,这样的话是比较可靠的, 大家可以看到结果是不一样的。 有了这样的结果,我们要找到第二个文件,相对于第一个文件哪些行进行删除,哪些行进行竞争,相信大家就知道怎么办了。我们需要做的就是找出小于号和大于号这两种数据即可, 当然也可以通过命令进行,比如说我们在第一步之后用 greep 只把大于号的结果找出来, 大于号呢,代表是在第二个文件中新增的内容,但是这样的结果可能不是符合我们逾期的,我们如何把大于号及后面的空格去掉呢? 大家其实可以使用卡的命令继续进行操作,卡的我们 卡特从第三个字母开始,后面的内容取出来就是卡特杠 c 三减号,大家可以看到我们只把新增的 id 找出来了, 同样的方法我们可以找到已经被闪出的 id, 幺幺零幺零五就是闪出的 id。

说下虚拟 dom 中的 deep 算法。虚拟 dom 是现代前端框架中常用的一种技术,它可以在内存中构建一个虚拟的 dom 数,然后通过比较新旧虚拟 dom 数来计算出需要更新的部分,最终只对需要更新的部分进行实际 dom 操作, 从而提高页面更新的效率。而在虚拟 dom 中,这个算法是计算新旧虚拟 dom 差异的核心算法之一。这个算法是一种低规算法,他从虚拟 dom 竖的跟节点开始,逐层比较新旧节点。在比较两个节点时, 先比较他们的类型及标签名是否相同,如果不同,则直接判定为不同节点,需要替换整个节点。如果类型相同,则继续比较节点的属性和此节点。在比较属性时, 如果新旧节点的属性相同,则不需要进行任何操作如果属性不同,则需要更新相应的属性。在比较子节点时,如果新节点没有子节点,而旧节点有子节点,则需要删除旧节点的子节点。如果新节点有子节点,而旧节点没有子节点, 则需要添加新节点的子节点。如果新旧节点都有子节点,则需要地规比较他们的子节点。在比较子节点时,如果新旧节点的子节点数量不同, 则直接判定为不同节点,需要替换整个节点。否则可以通过对子节点的 t 属性进行比较,来进一步优化 d 算法的效率。因为 t 属性可以帮助虚拟 dom 识别出哪些子节点是相同的,哪些是不同的。如果新旧节点的子 节点的梯值相同,则认为他们是同一个节点,可以直接附用旧节点的子节点。如果梯值不同,则需要将旧节点的子节点移动或替换成新节点的子节点。总的来说,的算法通过地规比较新旧虚拟 dom 书的节点, 可以快速计算出需要更新的部分,从而避免了无效的 dom 操作,提高了页面的性能。

家人们谁懂啊!改完代码提交 p 二,用传统 def 工具看变更时,整个人都麻了,明明只是把一个函数块移了个位置,缩了个进,结果显示一堆乱七八糟的行增删得逐行对着找半天眼睛都瞅酸了,效率低到想哭! but, 我 最近挖到宝了,必须给所有程序员安利这个开源代码审阅神器,必 def! 他 简直是代码变更的理解大师,专门解决传统 def 工具变更识别不准的痛点,再也不用跟碎片化的杭憎山结果死磕,真正做到一眼看透代码变更,谁用谁真香! 你们有没有过这种情况,复制代码中的函数进行重载,移动一个代码块,连续修改若干行这些常见的拷顶操作。传统的 def 工具,比如 get, 只能展示成一堆行删除和行新增,看得人眼花缭乱,还要自己手动比对关联,简直是折磨啊! 但是有了 b、 d、 f, 这些问题统统都不是问题了!他能识别快移动、快、复制等快捷操作,还能在行级层面检测行更新、行分割与行合并等精确行变更。这样一来,传统的荣誉编辑脚本就瘦身成功了,让你一眼就能看透代码变更的意图和逻辑。 而且 b、 d、 f 还能把差异结果表示成结构化的编辑脚本,支持编辑操作和差异显示的双向定位,省略效率 up up up! 它还有超贴心的细节支持,此串差异高亮,前后版本映设对比,甚至能切换紧凑对齐显示模式,白天黑夜主题随便换,简直是为开发者量身定做。 最绝的是,它不光能在官网直接用,还能作为插件装到 get 和 get up 中,直接集成到版本管理、团队协助和开源贡献的工作流理,无缝衔接开发场景,打工人狂喜 重点来了! biff 已经在 github gt。 gt。 link 等平台上开源用的是国产木兰许可证,放心用,不踩坑!不管你是个人开发还是团队协助,这个工具都能帮你告别代码审阅痛点,审阅效率飞起! 这是工具链接和 github 项目链接,宝子们赶紧去搜 biff 暴走,记得给项目点个 star! 程序员之间的宝藏安利!快分享给那些还在跟传统 diff 工具死磕的小伙伴们吧!

给大家分享一个 github 的小技巧, github 上随便找一个 p r, 在 uil 后面输入点 dif, 这样就可以拿到这个 pr 文本形式的 dif, 我们直接可以下载到本地 apply。

这么多年以来啊,我们教 ai 写代码的方式,可能从一开始就有点跑偏了。最近有项研究可以说是颠覆性的,它告诉我们其实存在一种全新的更接近我们人类思考的方式,而且这个新方法搞不好真的要彻底改变游戏规则了。 所以这就带来了一个最核心的问题,到底有没有一种更好的方法能让 ai 来写代码呢? 这个问题直接就引出了一场关于人工智能底层逻辑的大辩论,你看,这已经不止是两种技术在比较了,这根本就是两种哲学的正面交锋。 一边呢,是咱们的老熟人,久经沙场的卫冕冠军自回归模型,而另一边是一个全新的挑战者,潜力无限,它叫扩散模型。 好,那我们先来看看这位卫冕冠军自回归模型。你可能对这个名字不熟,但从 gpt 到我们手机里各种各样的 ai 工具,背后那个强大的引擎,其实就是它, 它的工作方式嘛,你想想你手机上的那个自动补全功能,然后把它,嗯,放大一万倍, 他就是这么干的,非常死板,从左到右,一个词接一个词的往外蹦,就好像一个作家,他只能看自己刚刚写完的句子,绝对不许往全看,也猜不到下句要写啥。 你看他的流程就知道了,非常现行,而且特别严格,给他哥开头,他就预测下一个词,加上去再预测下一个。这就好比开车上了一条单行道,你只能往前开,不能掉头,更别想跳到前面的路口去看看路况,一条道走到黑。 所以这最大的问题就来了,这种方式跟我们真人程序员写代码的习惯,那可真是差太远了。 你想想我们自己是怎么写代码的,肯定是先搭个大概的框架对吧?然后呢,回头再把细节填进去,写着写着可能又跳到另一个文件里去改点东西,整个过程是跳跃型的,根本不是一条直线。 好了,现在呀,让我们隆重介绍一下这位挑战者,扩散模型,他的灵感。说出来你可能不信,是从图像生成那个灵异来的,所以他的思路可以说是完完全全的。另一码事, 你再想象一个场景啊,这次你不是从一张白纸开始画画,而是拿到了一张非常模糊的满是藻点的草图。你要做的就是一步一步的把它变清晰,擦掉藻点,加上细节,直到最后一幅清晰的画就出来了。 没错,扩散模型处理代码就是这个逻辑。举个例子,它可能一开始只生成一个代码的股价,你看,开头是函数,结尾是返回结果,但中间最关键的逻辑部分全是空的,用这种 mask 符号占着位,它知道个大概,但细节嘛,完全没有。 接下来他就会开始去造,或者说填空。你看,他可能先填上一步,让整个代码的轮廓稍微清晰了一点,这个过程会来来回回做好多轮,每一轮这个代码都会变得更完整,也更正确。 这就是扩散模型最厉害的地方了,他根本不需要按顺序来,他甚至可以根据后面生成的内容再调过头去修改前面已经写好的代码。哎,你听听,这是不是就特别像我们真人程序员干的活了? 哎,理论听起来是挺美的,但真拉出来练练,它到底行不行呢?这个问题就得靠一个叫 stable diffuser 的 模型来回答了,它就是要把这个扩散理论真刀真枪地用起来。 这项非常了不起的研究工作,是来自字节跳动和华中科技大学的研究人员们一起完成的,而且它们设计了一个可以说是相当巧妙的实验。 他们想知道的核心问题其实很简单,如果我们把所有的条件都拉到一模一样,一样的计算资源,一样的数据,一样的模型大小,就只改变这个 o i 学习的方法。那么这种新的学习方法真的能训练出一个更厉害的 ai 吗? 这就是整个实验设计的精髓所在。为了保证这是一场绝对公平的对决,他们确保这两个模型除了学习方式不同,其他的一切从架构到数据全都是一模一样的。 唯一的变量就是,一个用老方法学,一个用新方法学好了,激动人心的时刻到了,实验准备好了,现在就把这两个模型拉到赛场上,让他们在好几个行业标准的编程能力测试里,真刀真枪的比一比, 结果呢,简直是一目了然。在一个叫 m h p p 的 专门考验解决复杂编程难题能力的测试里,你看,用扩散方法的模型得分是四十二点四,而老方法呢,只有三十六点二,挑战者完胜。 而在另外一个专门考代码编辑能力的测试里,这个差距就更夸张了,扩算模型的分数直接高了将近十分。这简直就是用事实告诉我们,在修改和完善代码这方面,它真的有天然的优势。 研究人员自己在论文的结论里也是这么写的,他们说扩散模型不光能跟上自归回模型,甚至还能超越他们。这可不单单是一次小小的胜利,这可很可能意味着一个全新方向的开启。 那问题就来了,扩散模型到底为什么能赢?因为它思考问题的方式更高级嘛。它不只是在傻乎乎的生成代码,它更像一个经验丰富的开发者,在不断地编辑和推理 这种更深层次的学习能力,甚至让它在那些训练数据比较少的编程语言上表现的也更好。那么聊了这么多,这一切到底意味着什么呢?我们是不是真的站在一个 ai 编程新纪元的门口了? 这次对决告诉了我们一个非常非常关键的道理,对于编程这种复杂的任务来说,教 ai 怎么学和教他学什么是同等重要的。 扩散模型这种新的训练方式,本身可能就是打开模型能力新上线的那把钥匙。这就给我们留下了一个特别值得思考的问题。 你想想,如果 ai 真的 能像我们人类一样,通过反复修改和打磨来学会编程,那么这种更灵活、更强大的学习方法未来还能用在哪些地方呢?是帮我们做科学研究还是进行艺术创造?这个想象空间可就太大。

好,下面呢,咱们就来自己手写这个 do 算法,那么在这呢,咱分为这么几步去走啊,第一步呢,就是先把虚拟节点这块给他写出来,因为有了虚拟节点,我们才能拿旧的虚拟节点和新的虚拟节点进行对比,从而把新的虚拟节点变为真实的节点啊,渲染到页面上 啊。这是分为这么三步去走,第一步我们需要写迅捷点生成,第二步我们需要写新的以及旧的迅捷点啊,他们进行一个对比,这也是定算法中的核心了。那第三步就是把新的迅捷点呸放到音乐上啊,分为这么三步去走,然后这一步呢,咱们先把这环境搭了,然后呢把那个迅捷点给他生成了,也就是 h 函数。我们这呢要写一下。 好,在我的桌面我先来一个 diss 这样的一个通路,然后呢,我需要把那个环境给他搭了,那就按照之前的这几步去走啊,只不过这的第三步就是那个 starbond, 我就不需要安了,因为我们要自己写了。前两步咱们要搭一下啊, 来到这儿我就进入到我的终端,然后把这儿呢投进去,然后 n p m 以 meet 杠 y 行,然后呢,再去把我们的 y pad 这块儿整个给它下载喽。好,稍微等它一下,然后呢,我把那个地方的 configure 也整个拿过来了。 好,拿过来以后我们看一下那咖啡梗啊。呃,我们的 g s 路口是 s r c 下的 index 加 g s。 来吧, s r c 目录下面有一个 index 加 g s。 好,然后呢,有一个 public 目录,嗯,里边有一个 index 加 t r 行,从而呢,我们需要把那个 g s 给它引入进来,呃,是线下的 index g s。 好,那么引进来以后呢,我一会看一下这儿会不会生效哈啊,当然,下载完事以后我们还需要把这 一个 dv 配置一下啊,这样呢,就方便我们这个启动,没有别的意思,看看 open 好了,按 pm 上 dv 就可以启动了。行,先把这呢稳稳的给他创建完事啊,然后呢,咱再往下一步去走,好,那么一也弹出来了,没有问题, 证明我们的搭建是没有问题的,是吧?小 kiss, 好,然后呢,咱们就开始写这个虚拟节点了,那么到这呢,生成虚拟节点,大家还记得在 sabbob 里面是怎么做的吧?咱 bobble 里面呢,是通过一个 h 函数对吧?啊,比如说我这来一个 let 啊 v note 一,等于, 哎,我写一个 div, 第二是对象,第三个呢,可能 div 里边有内容,比如说你好鸭,你好鸭,我记得你好鸭,看他们都是这个鸭,是吧? 你好呀,这是第一种方式。第二种方式呢,哎,我这有一个 reno 单 u l, 好注意啊,是数组了啊,然后这又有 h a b c 啊,然后你比花花木兰都沉默, 行,你看,就我自己说话,大家都不说话是吧,你以后花木兰花木兰都成花木兰啊,都沉默啊,行,然后呢,你看啊,我分为这么两种情况啊,当然咱们这写的比较简单了,我就说两种情况,第一种情况呢,就是你看到第三个三个是不是字母串类型啊, 然后你再看这样的第三个参数,是不是是一个速度啊?所以说呢,咱们要考虑是 h 函数啊,证明说 h 他是个函数,他所接收的参数有三,是吧?一二三,哎,然后呢,第三个参数的类型还不是那么特别确定,所以说一 一会我们肯定会看到什么第三个参数的类型,你是这个类型,哎,你就怎么样,你是这个类型怎么样?好吧,咱们先知道这事就可以了。那如果说我的这个 v note 一,他的第三个参数为搜串,那我这一旦打印的时候,他应该的格是什么德行?哎,咱们之间其实已经记录过了, 它是不是应该长这个样子,是吧,这儿只不过叫 div 嘛。啊,这个地方我们先不管它啊,然后这儿是不是你好压呀, 对吧,你应该长这个样子,这矛盾吗?各位啊,其实也矛盾,其实也不矛盾,就是你撒撒手,最后我要返回个对象,这个对象呢,有这么多 k 以及 y, 这是我们最终核心的,各位,好吧,那下面呢,咱们就先写这个 h 函数啊,那 h 这个函数搁哪来啊?我一会新建一个目录啊,首先是个到,哎呀哈,怎么变成了这个 demo 动啊,好,然后这里边呢,我来一个 h 点 g s, 然后这呢, sport 的 defent 来一个 function, 这不就是函数了吗,对吧?然后你这儿 import h from, 然后这儿点杠 dom 下的 h, 那么就引入嘞, 对吧?你这传了三个参数好了,那我这接嘛,把 s, e, r 对一下,然后这边再写一个,这是不是三个参数啊?啊,然后这三个参数,那你懂得。我先要判断第三个参数类型啊,如果 type of 说这东西它等于了 string, 那这边什么类型啊?说 h 的 h 函数的第三个参数是自动串类型, 这做上类型也意味着它是意味着它没有 他,没有儿子。哎,就这句话不对,他没有紫元素,就是有点太太不合适了,是吧?好,这是我们这的判断,然后这呢有个 s if, 然后再判断他可能是一个什么数组,对吧?是数组。哎,算了,一会咱们再说。先说这种情况, 如果这种情况的话呢,他会生成成什么呢?生成成这个德行,那这个呢,我教我教给这 v no 的函数去搞吧。 v no 的函数呢?他就是来生成的,好吧,来生成。好,那这呢,我们就需要写一个 v no 的,点击 s, 嗯,来 s part, 别忘了这是一个方形,他也是一个函数啊,他也是个函数啊,你看我这写括号嘛,然后这地方把这个 part vno 给他引入进来, 好,最后它生成的什么样子呢?最后它生成的这个结构也说它返回的是一个对象, 那这一方一定会返回个对象,那返回对象情况下呢?他有几个参数啊?有几个 j k 啊?一二三四五六,好家伙,六。那么那这样呢,我们就给他传六个,这样返回六个就可以了啊,传六个啊,分别是我这有不按照他的顺序了,比如说 s, e, l。 呃,这题 我看一下啊,这地方的这个 k 咱们就先不要了,好吧,后面咱们再加,然后这有一个,呃,这是 date, 然后第三个参数,它的一个 children 是没有的,那所以是 artifact, 然后再返回这个啊,还有一个,你看,好吧,第二个,第三个,第四个啊,分别以此类推啊,最终形成一个,呃,对象,当然你这几个,你反个个其实也可以啊,只是我希望它的格式啊,是这种格式。好,然后到这呢,我们就整个的也给它返回一下, 我们这接一下啊,需要到我们的 vino 这块接到,分别为 s e l date 以及修正和 text 和那个 aunt 啊,然后把这个返回一下 啊,然后这样的话,大家看的这不顺啊, e s 六的简洁表示法,我给它展示成这样, 好,那这就是我们的返回的一个续集点啊,然后这个地方是返回的,好了,咱们在这儿来看一下,是不是如愿所长哈。嗯,来 cons 这儿,他说 h 意思,哎,意思到挺笨的,是在我的盗墓下的 h 啊, 嗯,为什么呢?啊?刚才的问题啊,刷新一下就好了。然后呢,你看生成的它的丘顿是没有啊, 昂尼范的,对吧?然后这次呢?说一个对象啊,然后呢,呃,这个 animus, 这个咱后面再说啊, s e r 是不是 d l a, 然后 cats 是不是你,好呀,对吧?好,然后对应的这个参数咱们再来说一点啊,你看啊,我这儿传过去一二, an e found 三四五啊,一共传过去五个,然后这儿分别会接收 s e l, s e l 是什么?就这个 啊,也就说是这儿传过来 div, 那么 s cl 就是 div 喽,然后这个是哪个呢?这个就是这个空对象,那这儿的 data 和这儿 data 就是那空对象喽,然后第三个呢?是,你好呀,对吧?传过来,你好呀,那证明这儿的这个参数就是你好呀, 啊,这边的这个参数你好压,也就说是在我对象的一二三四,第四个咱们数一下啊,他这的结构是是有点乱的啊,咱们先不管这吧,一二三四,那也就说对应的是这个 text, 对吧,然后这 text 就是你好压啊,剩下的丘震和。 呃,这个 e l m 丘震和 e l m 分别为啊,你看是吧?这是第三个和最后一个啊,第三个和最后一个,那形成了一个虚拟的盗墓。好,当然这是我们的第一种情况,那第二种情况呢?它可能会长这个样子。 好,当长第二样子以后呢?它这儿呢,就什么都不会打印了。为什么呢?是因为我们这儿并没有判断它为数组情况,就第三个参数为数组啊,判断一下 s if 啊,判断数组,判断一个变量。是不是数组方式太多了啊?可以通过呃,这 instead of 对吧?或者说可以通过它的一个原型啊,它的 contractor 是不是 arrow 啊?还可以通过 arrow 的 e, 是吧?通过这样的判断,判断他是不是一个数组,如果说他是一个数组,那我们的秋日里边就应该有,那 对吧?那我们就需要把第三个参数先给他打印出来第三个参数是啥了,就剩一个数组了吗?咱们要把它便利放到丘镇里边。那所以说我这来一个便利 啊,那咱们就通过 light item of of, 然后这有一个第三个参数便利。这个啊,数组便利。数组以后呢,我这写一个变量为求准码 为数数,然后呢,把每一个对象给它铺持到这个数数中,然后最终我们要 return 为 note, 是吧?那么它的 s, e, l 我们要给传过去,这个叫传过去啊,它的第三个参数就是受阻了,就区准了,然后后面就安迪贩子了,就是你的 tax 和 e l m 是奥迪贩子了啊,这是我们传过去的。那传过去以后呢?咱们再来看,刷新一下啊,看这个地方,你的 tax 就给安迪贩子了,对吧? 但是你的秋日里边,哎,又是每一项看到吧,你 l i 为 a 嘛,啊,这就是我们的一个虚拟节点,就算是构建了。那咱们总结一下,虚拟节点呢,其实就是通过 h 函数啊,传递到这个 wenote 啊, wenote 呢,最终生成了一个对象的结构,这就是虚拟节点 啊。然后这地方呢,是判断的啊,这地方啊,判断的 a 是函数的第三个参数是不是数组啊?如果是数组, 把它放到这吧,如果是数字组,那么就意味着,意味着啊,有 子元素啊,有子元素,好,这就是我们这一块整个的一个内容。那么行,这节课呢,咱们就算是把虚拟节点给他构建出来了,分别为两种情况,当然这样呢,咱们写的稍微的简单了一点,其实还可以判断很多很多东西的, 咱们先是以主要的写完啊,并且了解定算法的整个核心为目标往下去走,代码的不严谨呢,咱们就后面后续再去添加,比如哪一块不合理,到时咱们再去添加。当然了,可能他第三个参数,比如传的就是个这个,那么哪都不会进入了,结果呢,就是一个,呃,可能结果就成这个样子,是吧? 所以说呢,这判断并不是那么特别严谨,因为这个判断除了你是不是 string, 可能还说你是不是一个 number 也可以,对吧?那在这呢,咱们就不判断了,就说这么,呃,一个是这个情况,一个是这个情况吧。好吧,行,那本节课呢,咱们针对 h r 就先说到这。

同学们大家好,我是金城智能马工,今天我们来学习一下 get def 这个命令,它可以用来查看文件在工作区、暂存区以及版本库之间的差异,它还可以查看文件在两个特定版本之间的差异,或者文件在两个分支之间的差异。我们平时开发过程当中 更多的使用的是一些图形化工具,但是了解一下 git diff 这个命令还是很有必要的,因为有的时候我们需要在一些没有图形化工具的服务器上使用 git git diff 命令后面如果什么都不加的话,会默认比较工作区和暂存区之间的内容,它会显示发生更改的文件 以及更改的详细信息。下面我们来演示一下还是使用上一节课创建的仓库,这个仓库目前有三个文件,而且有三次提交, 每一次提交都是新增了一个文件,比如说 file 一 点 test, 里边是幺幺幺,然后第二次提交增加了 file 二点 test, 第三次提交 file 三点 test。 get diff 这个命令非常的简单,我们先来修改一下 file 三这个文件, 这里我们把内容改成 hello world, 保存退出一下。我们现在使用 get def 这个命令查看一下它默认比较的是工作区和暂存区之间的差异,可以看出刚才的差异已经显示出来了, 这里输出的第一行表示发生更改的文件,第二行我们稍微解释一下。 get 会将文件的内容使用哈希算法生成一个四十位的哈希值,这里只显示了哈希值的前七位, 后面的幺零零六四四,它代表的是文件的权限。再往下就是修改的内容了,红色文字表示删除的内容, 绿色文字代表刚刚添加的内容。我们现在比较的是工作区和暂存区之间的差异,因为我们修改的内容还没有添加到暂存区,现在我们来添加一下,然后再看一下输出结果, 可以看出刚刚比较的差异性现在已经不存在了。除了比较工作区和暂存区之间,我们还可以比较工作区和版本库之间的差异,在命令后边直接加上 hit 就 可以了, 比如我们现在还没有将添加的内容提交到仓库里边,而这个差异的内容又出现了,这是因为我们刚刚还没有进行提交操作,所以说工作区和版本库之间的内容是不相同的。我们还可以比较一下暂存区和版本库之间的差异, 在 get diff 命令后边加上 catch 就 可以了, 可以看到输出的内容是相同的,那我们现在来提交一下, 然后我们再使用 get diff 来比较一下, 可以看出暂存区和版本固之间的差异已经不存在了。 get diff 命令除了可以比较工作区、暂存区、版本固之间的差异以外,还可以比较两个特定版本之间的差异,用法就是在后边加上两个版本的提交 id。 我 们先来看一下当前仓库的提交记录, 我们比较一下最新两次提交的版本, 可以看出最新两次提交版本也已经显现出来了。 除了使用提交 id 之外,我们还可以使用 head 来表示当前分支的最新提交。 head 是 get 当中一个非常重要的概念,它指向分支的最新提交节点,在后面的学习当中我们也会经常用到,我们可以使用某一个版本的提交 id 和 head 进行比较, 这里我们可以改一下, 可以看出和刚才的输出结果是一样的。当然如果我们每次比较都要查看 id 的 话,确实有些麻烦。 我们经常用到的就是比较当前版本和上一个版本之间的差异,这里 get 也给我们提供了一个更加简变的方式,就是我们使用 head 加上波浪线来表示上一个版本,那么刚刚的比较就可以改一下, 可以看出和刚才的输出内容还是一样的。当然这里的波浪符号也可以改成尖角号,也是表示上一个版本。我们还可以在波浪线前面加上具体的数字,它表示当前版本的前几个版本。 head 波浪线二,它代表当前版本的前两个版本和当前版本的一个比较, 我们可以看一下波浪线三,这里我们查一下提交日期 前面的这个 head 波浪号三,它代表的其实就是第一次提交,而第一次提交和当前提交有哪些区别?就是新增了两个文件 file 二和 file 三,这里也体现出来了多了一个 file 二文件和一个 file 三文件。 get def 后面加上文件名也可以查看这个文件的差异,当然如果这样比较的话,就只会显示当前文件的一个差异,其他的差异就不再显示了,这里我们来比较一下, 我们比较一下 there 三点 test, 可以 看出它只显示了一个 hello world, 刚刚显示的这里的 第二个文件 feel, 二点 test 已经没有显示了。 get diff 还可以比较两个分支之间的差异,加上两个分支的名字就可以了。这个等到我们后面学习完分支的内容再来讲解。好,今天的内容就到这里,我们下节课再见,谢谢大家。

别人用一个 ai, 我 同时用六个,不是我卷,是这个方法太香了。大家记住这个工具,它能同时调用六个 ai 模型,各干各的活。比如我让 deepsea 写大纲,让可乐的润色文案,让 gpt 做翻译,三个同时跑,互不干扰。 最绝的是这个功能,同一个问题,六个 ai 同时回答,直接对比,选最好的那个,三十多个主流模型随时切换。以前要开六个网页,现在一个界面搞定,用过的回来告诉我省了多少时间。

看一下这道面试题,请减速其低速算法的工作原理,近期需要想面试的同学建议来领取一份简单面试宝典。八股文、性能优化、工程化、商业题等等都有非常详细的讲解与 代码识例。低速算法的核心是为了解决传统数对比性能低下的问题,它采用了 o n 的 启发式算法,其原理主要基于三个假设,第一是同层比较,二层级直接重建。第二是组建隔离,同类型组建直接替换。第三是 k 标识同, 通过 k 来判断元素是移动还是新建。在具体实验上, react 采用 faber 架构,将对比任务飞片,而 v o 三则通过静态标记而过,静态内容对比,进一步提升了 d f 效率。我们采用一个象棋的 virtual dome, d f 实现,整体逻辑分为三层,主 d f 入口对比属性对比子节点。它的工作逻辑非常显性, 第一看在不在,不在了就标记。第二看变没变。如果是原来普通的 dvd 变成了 spa, 或者主键类型变了,那没法复用,直接换新的。第三步,如果骨架没变,我们就看细节,通过 dfplus 查属性变没变,通过 df 求准查里面的紫元素变没变。 dfplus 函数专门人负责处理 id、 class style 等属性的变化。如果新的有,旧的没有,或者两者不一样,那肯定以新的为准。如果旧的里面有某个属性,如 class name 在 新的里面找不到了,说明开发者把它删了, dom 会把这个属性移除。 def 求准指节点对比,这是最难的部分, 是 k 发挥作用的地方。为了让大家看懂,我们实现一个带有 k 元素的简化版本。在 mark 里,首先做了一件最重要的事,建党。把所有的拒绝点按 k 存到一个 map 里。新节日来了,他拿自己的 k 去 map 里查,如果查到了,直接复用。虽然位置可能变了,但不用重新构建洞,只用地规调用 def 去修补一下属性就行。自己大家注意, def 求准你又调用了 def, 这是第一规逻辑闭环的,如果没查到,说明他是新来的,要标记 insert, 那 老师是新建。如果你不写 k, 代码默认用 next to k, 按顺序乱的全乱套了。有了 k 第一步算法才能精准的赋用节点。

让 ai 编程效率提升十倍的神器来了!出自英国伦敦的 bros ai 团队,它是全球首个专门用来管理 ai 编程助手的看板工具。这个项目能让你同时运行多个 ai 编程助手并行工作, 彻底告别定在终端干等的日子。支持 crow、 crow、 openai、 cox、 jimmy c l i 九款主流 ai 编程助手一键切换, 利用 gitworks 技术,让多个 agent 互不干扰的并行执行。内置代码 diff 工具,像审查 pr 一 样轻松地 review ai 写的代码。 evellevs 生长负责人评价说,这自 cut 之后,生产力提升最大的工具 完全开源,免费一行命令即可启动,赶紧去试试,这可能就是 ai 编程时代的效率突破口!