1.本周学习总结

1.1思维导图

1.2.谈谈你对线性表的认识及学习体会

经过几周线性表的学习,对线性表有了一定的了解。
线性表就是对以前知识的延伸吧。顺序表的本质是数组,也就是把数组和数组的长度定义在一个结构体里面,操作的时候注意对数组长度进行改变。链表是在以前学习的链表的基础上加了循环链表和双链表,我终于明白了老师在上学期学习C语言的时候说:“下学期学数据结构,链表就用得多了。多了。”顺序表和链表各有千秋,一个便于访问,一个便于修改,链表还可以解决元素数量不确定的情况,所以这二者在使用时应该灵活。我在做PTA7-1的题目时,尚没搞清楚二者的区别,导致在顺序表和链表的使用上发生混乱,只得重做。
而且,对先线性表掌握熟练,对以后(起码第三章的栈)的学习也是有好处的吧。

2.PTA实验作业

2.1 顺序表操作集

2.1.1设计思路

List MakeEmpty()
直接建顺序表,给Last一个无效的长度

Position Find( List L, ElementType X )
遍历 int i;
for i=0 to L->Last
if 找到X,返回X的位置i
end if
end for
如果没找到,输出没找到。

bool Insert( List L, ElementType X, Position P )
先判断顺序表是否是满的
if L->Last+1==MAXSIZE
输出FULL
end if
再判断P的位置是否合法
if P<0或者P>L->Last+1 //P的位置是负的或者P溢出
输出ILLEGAL POSITION
返回false
end if
如果都成立,先从后往前移动数组,再插入数据
for i=L->Last to P
数组的后一个数等于前一个数
空出L->Date[P]
end for
再P的位置插入X
数组长度加一

bool Delete( List L, Position P )
先判断P的位置是否合法
if P<0或者P>L->Last//P的位置未负或P溢出
输出POSITION P EMPTY
返回false
end if
如果条件成立,删除数据
for i=P to L->Last
前一个数等于后一个数
end for
数组长度减一

2.1.2代码截图



2.1.3本题PTA提交列表说明。


Q1:有没有犯低级错误?
A1:在删除元素的函数中,如果找不到P的位置,应该输出P找不到,此时P不是P。而是要输出一个位置,我没有发现,直接复制粘贴过去,导致好久才发现这个错误。
Q2:这道题敲完之后,题目样例可以输出,但为什么全是答案错误?
A2:这道题,是完全的C语言题目,不能用任何C++语法,因为对malloc函数掌握不熟练,导致错误。(确实C++比C好使,不过语法该掌握还是要掌握)
错误的malloc语句
正确的malloc语句

2.2 jmu-ds-有序链表的插入删除

2.2.1设计思路

函数题,主函数和一些次要函数已经给出,尽量去看懂主函数在干嘛,如果看不懂,就直接写函数吧。

先按要求创建一个链表。
插入函数:
LinkList p=L;//去链表L
LinkList s //插入的临时结点
遍历p
while(p)
if p的下一个结点没有元素 //e要查到最后
把e的数值赋给s
尾插法插入结点s
end if
else if 要插的位置不在最后 找到插入位置
把e的数值赋给s
头插法插入结点s
end if
end while

删除函数:
LinkList p=L;//去链表L
LinkList s //插入的临时结点
遍历p
while(p)
if 发现要删除的数据
将要删除的结点赋给s
断链再合链
释放s的内存
end if
end while
遍历p后,如果没有找到要删除的数据e,
输出 找不到!

2.2.2代码截图

插入函数

删除函数

2.2.3本题PTA提交列表说明。

自从学了数据结构,从段错误到答案错误也是一种进步啊
Q1:这道题遇到的最大的障碍是什么?
A1:现在学的链表和之前学的链表一个很大的区别就是:现在学的链表是带有头结点的。因为一开始我并没有重视这一块,导致我在遍历链表,修改链表数据的时候对pp->next的认识不足,因此出现了很多的段错误,死循环。还有一个比较低级的错误,就是我的if后面又加分号了……
Q2:你真的认为PTA上的函数题,一些题目已经给出的函数就一定不会出问题吗?
A2:一开始我是很相信题目给的函数的,直到做了这一题……这道题有两个测试点,一个是数据的插入删除,一个是空链表,一开始我的代码各种运行超时段错误的时候,空链表的测试点是可以过的,后来我发现了问题,并改正,但是我的第二个测试点又过不了了。我当时也很惊讶吧,因为空链表的函数是题目给的啊,后来在最后的判断e是否存在的if里加了条件,之前是这样的
其实,说到底,还是自己不行,如果是空链表,直接输出空链表,就没有这元素那元素找不到的输出了。

2.37-1 两个有序序列的中位数

2.3.1设计思路

排序函数(二路归并法)
同时遍历链表L1,L2;
while L1&&L2
比较L1->data与L2->data的大小,取较大的
被取值的链表向后移动,另一个不动
当L1或L2遍历完的时候,循环结束
end while
将剩下没有完成遍历的链接在后面
if(p1)
p->next=p1;
L1->next=NULL;
end if
if(p2)
p->next=p2;
L1->next=NULL;
end if

2.3.2代码截图

头文件,函数声明以及主函数

建链表的函数

二路归并排序


找中位数

2.3.3本题PTA提交列表说明。


Q1:感受如何?
A1:这个题目可以说是我的开窍题吧(当然开的不是那么厉害),这个题让我明白了顺序表和链表的区别…一个是数组,一个是链表,当初第一次做这个题的时候完全混乱了,在定义结构体体的时候又是链表,又是顺序表(之前的代码删了,不然是一个完美的反面教材),后来上课明白了,才换成链表来写,当然,链表用的也不是那么好,因为在最后输出中位数的时候我还是用了极为浪费空间的数组。
Q2:最后的数组可以不用吗?
A2:我觉得可以吧,可以把数组长度设成全局变量或者通过传参传到最后的RankList函数,然后for循环遍历链表,输出对应的值,这样还可以少遍历一半链表,效率更高。

本题不用删除重复数据……不然最后一个测试点过不了……×3

3阅读代码

3.1 题目


3.2 解题思路

题目在数组的处理上和上次做的日期抽象数据类型中的日期计算器差不多
都是相当于一个循环数组,当一轮循环完毕后边对数组的下标进行初始化(在这里我认为也可以用循环链表)
每次遍历到一定的次数是,淘汰掉一个人,然后继续遍历,直到所有人全部淘汰。

3.3 代码截图

3.4 学习体会

数据的存储结构就两种,一个是顺序表,一个是链表,二者各有长短,有时都可以解决问题,
有的时候顺序表好使(比如访问次数比较多 ,元素数已知),有的时候链表好使(比如要多次对数据元素进行增删改的操作,
要灵活运用。