20182330《程序设计与设计结构》 第十周学习总结
教材学习内容总结
周一: 树
- 树的定义:树是有n个结点组成的有限集合
n=0,为空树
n》0,有特定节点为根
- 特色:非线性结构:一个前驱多个后继 。 其余(除根)到根的路径惟一
- 结点的度:结点的子树数
树的度:结点的最大度数
叶子:度为0
-
- 分支点:非终端结点
- 结点的层次:根为第一层
- 树的深度:结点的最大层次
- 有序树无序树
- 树和森林
- 树的基本操做
- 存储结构
define M 100
class PTNode{
ElemType data;
int parent}
class tree
{
PTN items[M]
int root;
int n;
- 孩子表示法
多重链表
孩子链表(相似于链地址法)
- 双亲孩子表示法
结合1 2方法
- 孩子兄弟表示法(左孩子右兄弟)
二叉树
- 结点至多为2,子树有左右之分
- 第i层最多有2^(i-1)个结点
- 深度为k最多有2^K-1个
- 叶子比子节点多一n0=n2+1
两种特殊的二叉树git
满二叉树
深度为k: 2^k-1
每层:2^i-1算法
彻底二叉树:满去掉最下层最右边数组
二叉树的遍历(递归性)!!数据结构
- 先序:先根后左右
- 中序:先左后根再右
- 后序:左右根
- visit函数 前后没法肯定
周三:遍历
- 查询二叉树的某个结点
- 统计叶子结点个数
- 求二叉树的深度:
左右子树最大值加一。后序遍历
- 层序遍历
周五:堆
- 彻底二叉树:结点小于或等于左右孩子
包含一样数据的最小堆(小顶堆)不必定同样
- 插入与重排序
做为叶子结点插入,且要保持数的彻底性
插入位置:h层最右边空位置(原来不满);h+1层第一个位置
- 删除
- 删除最小值,重构堆
- 删除root,把最后一个叶子移动到根再调整
- 用顺序存储合适:更快定位索引
- 根拿出来组成有序区,筛选调整,(无序区首尾交换)
教材学习中的问题和解决过程
- 问题1:什么叫树的模拟连接策略?

- 问题1解决方案:这种方式使得元素可以连续存储在数组中而不用考虑该树的彻底性。所以不会浪费空间,可是该方式增长了删除树中元素的成本。
- 该数组的每一元素都是一个结点类,每一节点存储的是每一孩子(可能还有其双亲)的数组索引,而不是做为指向其孩子(可能还有其双亲)指针的对象引用变量。
- 优势:这种方式是的元素可以连续存储在数组中,所以不会浪费空间。
- 缺点:该方式增长了删除树中元素的成本,由于它要么须要对生育元素进行移位以维持连续状态,要么须要保留一个空闲列表。
通常而言,一棵含有m各元素的平衡n元树具备的高度为lognm。函数
- 问题2:上课的时候没有听懂左旋和右旋?
问题2解决方案:左旋右旋指的是AVL树(高度平衡的搜索二叉树
一棵平衡树,或是空树,或是具备如下性质的二叉搜索树:左子树和右子树都是AVL树,且左右子树的高度之差的绝对值不超过1。 )的平衡化旋转。
AVL树相较于普通的二叉搜索树,自主要的就是作了平衡化处理,使得二叉树变的平衡,高度下降。
在插入一个结点后应该沿搜索路径将路径上的结点平衡因子进行修改,当平衡因子大于1时,就须要进行平衡化处理。从发生不平衡的结点起,沿刚才回溯的路径取直接下两层的结点,若是这三个结点在一条直线上,则采用单旋转进行平衡化,若是这三个结点位于一条折线上,则采用双旋转进行平衡化。学习
左单旋

右单旋

双旋转

代码调试中的问题和解决过程
- 问题1:明白算法,可是不知道如何输出一棵树?有哪些输出方法?
- 问题1解决方案:
- 条形输出:输出的结果是[[[1] 3 [[4] 6 [7]]] 8 [10 [[13] 14]]](没有树型)
void puttree(tree t){
if(t==NULL)return;
else{
putchar(‘[‘);
puttree(t->left);
printf(“%d ”,t->data);
puttree(t->right);
putchar(‘]’);
}
}
- 躺着输出(第一次看到这种输出方法)
能够输出一个树形,可是须要歪着头看
char bra[]={"-/\\<"};
void puttree(tree t,int h){
int i;
if(t!=NULL){
puttree(t->right,h+1);
for(i=0;i<h;i++)putchar('\t');
printf("%d",t->data);
putchar(bra[
((NULL!=(t->left))<<1)
|(NULL!=(t->right))
]);
putchar('\n');
puttree(t->left,h+1);
}
}
- 缓冲区输出(没有太理解,暂且不在这里放代码)
本身定义字符缓冲区,先把树形画到缓冲区上,再把缓冲区的内容写到屏幕。对于排序二叉树,须要申请的字符缓冲区大小至少是高为logn宽为n。
- 问题2:优先级队列能不能像普通队列那样循环?
- 他们的实现不一样,普通队列是用线性数据结构来实现的。优先队列使用二叉堆来实现的,是非线性结构,保证了它的插入删除时间复杂度都接近O(log2 n);实现不一样,能作的功能也不一样,优先级队列也没法实现循环遍历。

上周考试错题总结
上周无考试spa
结对及互评
点评过的同窗博客和代码
- 本周结对学习状况
- 20182314
- 点评:知识点总结的较为详细,对二叉树的理解很到位,排版简洁,值得学习。
基于评分标准,我给本博客打分:15分。得分状况以下:
感想,体会不假大空的加1分
排版精美的加一分
结对学习状况真实可信的加1分
正确使用Markdown语法
模板中的要素齐全(加1分)
错题学习深刻的加1分
点评认真,能指出博客和代码中的问题的加1分
教材学习中的问题和解决过程, 加5分
代码调试中的问题和解决过程,加2分
- 上周博客互评状况
其余(感悟、思考等,可选)
堆的学习是在以前二叉树的基础上,其实优先级队列就是将堆进行一次封装,都调用了堆的函数。.net
学习进度条
目标 |
5000行 |
30篇 |
400小时 |
|
第一周 |
42/42 |
2/2 |
20/20 |
|
第三周 |
394/471 |
2/4 |
25/45 |
|
第四周 |
394/471 |
2/4 |
25/45 |
|
第五周 |
1668/2139 |
2/6 |
35/80 |
|
第六周 |
2388/4527 |
1/7 |
30/110 |
|
第七周 |
1660 /6187 |
2/9 |
25/135 |
|
第八周 |
1660/7847 |
2/11 |
20/130 |
|
第九周 |
1660/9507 |
2/13 |
25/155 |
|
第十周 |
1144/10651 |
2/15 |
30/185 |
|
计划学习时间:25小时设计
实际学习时间:30小时
改进状况:但愿提升效率
参考资料