数据结构与算法
文章平均质量分 55
__空无一人__
通过我的文章认识我!
展开
-
多叉树和二叉树的互转及多叉树森林和二叉树的互转
二叉树结点采用孩子兄弟链结构存储,把多叉树的第一棵子树转换的二叉树作为二叉树根的第一个孩子,把多叉树的第二棵子树转换的二叉树作为二叉树的第一个孩子的兄弟,把多叉树的第三棵子树作为其第二棵子树转换的二叉树的兄弟,以此类推。把二叉树的第一棵子树转换成的多叉树作为多叉树根的第一棵子树,把二叉树第一棵子树的兄弟树转换成的多叉树作为多叉树的第二棵子树,依次类推。把森林中的每一棵多叉树转换为一棵二叉树,然后把这些二叉树以兄弟链的形式结合在一起即得。把二叉树沿着兄弟链拆成一个二叉树集合,把每一个二叉树转换成多叉树即得。原创 2024-05-24 08:53:29 · 505 阅读 · 0 评论 -
树的线索化
中序遍历二叉树,设置prev指向前一个访问的结点,curr指向当前访问的结点,若prev结点没有右孩子,则设置它的righttag为1,并让rightchild为curr,表示prev结点的后继为curr,若curr结点没有左孩子,则设置它的lefttag为1,并让leftchild为prev,表示curr结点的前驱为prev。像上面所说,二叉树的分支要么指向它的孩子,要么指向它在遍历中的前驱/后继,为了加以区分,需要给二叉树的结点增加一个flag来指示分支是指向它的孩子还是它在遍历中的前驱/后继。原创 2024-05-21 09:46:05 · 399 阅读 · 0 评论 -
树的序列化
在python里面有个模块pickle专门实施对对像的序列化,序列化之后得到的是一个二进制的字节流,当然我们可以用它来对树这种数据结构来进行序列化,不过如果树的结点的value是字符串,那么可以对树进行一个轻量级的序列化,这里来讲讲这个。原创 2024-05-16 16:15:09 · 484 阅读 · 0 评论 -
矩阵的压缩存储
cin2(Q的第i行)的值的一部分,可以预设一个初始值为0的数组larr来存放Q的一行的各个矩阵元的值,序列中的项aij * bjk加到larr[k]中(larr[k] += aij * bjk),我们按照列号从小到大的顺序依次让M中第i行的元aij和N的第j行进行上面的相乘处理,最后就能得到Q的第i行,我们按照行号从小到大的顺序依次对M的行执行上述的操作,便能按照行号从小到大的顺序依次得到Q的各行,也就能得到完整的Q了。拿M的第i行和N的所有列去相乘,要得到Q,怎么做呢。原创 2024-05-07 13:48:17 · 941 阅读 · 0 评论 -
python实现2路归并排序
对于一个序列a1 a2 a2 …an,我们让a1和a2合并,a3和a4合并,依次类推,最后得到一个有序子序列的序列a1 a2;an-1 an,接下来让a1 a2和a3 a4合并,a5 a6和a7 a8合并,以此类推,得到一个更大有序子序列的序列a1 a2 a3 a4;算法实现的难点和需要注意的地方在于边界情形,子序列两两配对的时候,可能最后有一个子序列落单了,找不到另一个子序列了,还有两个子序列进行合并时,我们交替得把两个序列的切片首尾接在一起,要注意最后一个切片的处理。原创 2024-05-04 10:50:24 · 539 阅读 · 1 评论 -
python实现的堆排序
先来看怎么解决问题(2),假设堆顶元素取序列中的最小值,根据堆的定义,堆的任一子堆还是堆,假设输出堆顶元素之后,把数组当中最后一个元素ak放到了堆顶位置(取数组最后一个元素不会破坏左右子堆的堆性),原堆的左右子堆的堆顶元素是分别ai和aj,那么ai、aj、ak三者之中最小值将成为新堆的堆顶,如果是ai,则ak和ai换位,如果是aj,则ak和aj换位,如果ak仍然是最小的,什么都不用做,调整结束。数组下标从0开始,如果我们把ai存放到数组下标为i-1的位置,那么ai的子结点的数组下标是2i+1和2i+2。原创 2024-05-03 20:36:08 · 763 阅读 · 2 评论 -
python实现的冒泡、快速排序
ai是满足最大值在最右边的序列,求a1 a2…ai ai+1满足最大值在最右边的序列,若ai原创 2024-05-01 18:33:26 · 1178 阅读 · 0 评论 -
python实现的基于单向循环链表插入排序
相比于 中定义一个循环双向链表来实现插入排序来说,下面的实现采用一个单向循环链表来实现,并且不需要定义一个单向循环链表类,而是把一个list(数组/顺序表)当成单向循环链表来用,list的元素是一个包含两个元素的对象,一个是数值,一个是指向下一个list元素的指针(list的元素下标),list的第一个元素(下标为0的元素)是单链表的头结点,它不存放数据,起到哨兵的作用。第一种,可以new一个空的list,遍历链表,依次把访问到的元素append到list中,最后返回这个list。有两种方式来实现这一点。原创 2024-04-30 15:10:46 · 741 阅读 · 1 评论 -
python实现的折半插入排序
这可以通过归纳总结出来,折半查找的过程其实就是在不断缩小待插入数据应该被插入的范围,这个范围记为[low, high],当这个范围缩小到1的时候,也就是low等于high,再缩小就没法缩小了,这个时候mid等于low和high,待插入的数据,当它比source[mid]小,那么待插入数据应该插在mid的位置,mid及后面的数据应该后移,根据逻辑执行了high = mid - 1之后跳出循环,所以跳出循环之后待插入数据应该插在mid位置也就是high + 1位置。原创 2024-04-28 14:25:20 · 287 阅读 · 0 评论 -
python实现插入排序
基于循环双向链表实现的插入排序,循环双向链表见前作。原创 2024-04-27 18:18:38 · 397 阅读 · 2 评论 -
python实现的循环双向链表
【代码】python实现的循环双向链表。原创 2024-04-27 16:50:48 · 318 阅读 · 2 评论 -
关于yield from的深度剖析二
谈一下yield from递归,它看起来不像普通函数递归那么直观,如果我们把调用过程用一棵树来表示,得到一棵调用树,yield from调用作为中间结点(非叶结点),yield语句是访问结点的动作,执行生成器yield from语句就是由一个结点下降它的一个子结点上,执行生成器的return语句或者后根遍历执行完yield语句,就是由一个结点回溯到它的父结点,所以基于yield from实现树的遍历就很方便了。下面给出一个基于yield from实现的遍历访问UserList类型树的算法。原创 2024-04-16 11:00:26 · 276 阅读 · 0 评论 -
谈谈python里的协程
任意的两个协程coroutine a和coroutine b,如果coroutine a不是由coroutine b交换而来,它可能是第一个执行的coroutine,也可能是由另一个coroutine c交换而来,我们把coroutine a交换到coroutine b定义为ENTER,如果coroutine a是由coroutine b交换而来,那么coroutine a再交换到coroutine b,我们把它定义为YIELD。普遍上的定义是说协程是用户空间的线程,也叫纤程,轻量级的线程。原创 2024-04-14 18:10:33 · 380 阅读 · 2 评论 -
正整数拆分问题
下面让我们来研究一下如何拆分一个正整数,举例来说,对3进行拆分,很容易给出所有拆分的情形,3=1+1+1,3=1+2,3=2+1,3=3,为了简化输出,我们把3=1+2和3=2+1看成同一种拆分,我们以3=1+2代表了,也就是设定拆分序列为正序。你可能会疑惑,很重要吗?好像不很重要,因为似乎没啥实际的用处,无论是学习还是工作,没有遇到过这种需求,但其实它非常重要,如果你曾经遇到过一个问题,n个结点的树,它有多少种形态,这个问题数据结构与算法的书里有答案,但如果要你画出所有树的形态,你画得出来吗?原创 2024-03-30 17:10:39 · 402 阅读 · 0 评论 -
输出所有的排列组合
需要注意的是前面步骤挑出的数在后面不能再出现,也就是要记住前面步骤里已经挑选的数,还要注意的是当输出了一个排列,要计算下一个排列的时候,并不是又要从第一个数重新开始挑,而是采用回溯法,从最后一个数开始,为它挑一个新数,如果还可以挑出一个新的数,挑出那个数,前面的数保留不变,输出排列,如果不能再挑出一个新数,则回退到倒数第二个数,为倒数第二个数挑出一个新的数,然后挑最后一个数,输出排列,如果不能为倒数第二个数挑一个新数,则回退到倒数第三个数,以此类推,下面看代码实现。这是排列的情形,那么组合呢?原创 2024-03-30 15:34:16 · 397 阅读 · 0 评论 -
一个四则运算器的实现
python实现的四则运算计算器原创 2024-03-29 11:51:23 · 437 阅读 · 0 评论 -
霍夫曼树为什么是最优二叉树?
霍夫曼树之所以是最优二叉树的归纳原理原创 2024-03-28 13:45:46 · 813 阅读 · 1 评论