1.本周学习总结#
1.1思维导图##
1.2.谈谈你对线性表的认识及学习体会##
通过线性表的学习,对链表有了更进一步的认识和掌握,链表相比于以前的数组,它对数据的插入、删除,方便了许多,是一种更高效的做法,不用通过挪动数组来插入、删除,只要改变链连接的结点即可。而有序表的操作与数组类似,也是通过移动来插入、删除数据。
上学期也学习过一点链表,但只是粗略的知道有链表这种数据结构的概念,通过这次的学习,学到了链表的一些基本操作,也发现了链表的优点。
2.PTA实验作业#
2.1.题目1:顺序表操作集##
2.1.1设计思路(伪代码)###
查找函数
定义i为Data数组下标
for i=0 to L->Last+1
如果找到数据X
返回i
end for
返回ERROR
插入函数
定义Data数组下标i
if 未插入数据时,顺序表里数据个数已经等于MAXSIZE-1
输出FULL
返回false
end if
else if 插入位置在第一个数前面或在最后一个数的后面的后面位置
输出ILLEGAL POSITION
返回false
end if
else
for i=L->Last+1 to i>=P
把前一个数据放到i这个位置
end for
把X赋值给L->Data[P]
L->Last++;
返回true
end if
删除函数
定义Data数组下标i
if 要删除数的位置不在顺序表范围内
输出POSITION P EMPTY
返回false
end if
else
for i=P to L->Last
把第i+1个数往前移
end for
L->Last--
返回true
end if
2.1.2代码截图###
2.1.3本题PTA提交列表说明###
Q1:一开始题目较长,函数又比较多,题目意思不是很理解,Devc上代码写好后,测试时输出结果与题目不同
A1:第一个函数要求创建并返回一个空的线性表,我一开始是L->last=0,但输出结果总是错的,后来看了网上一些代码,发现L->last=-1才是。若L->last置为0,则插入5个数,实际只有4个数被插进去
Q2:输出结果和题目的一样后,开始提交,一直是答案错误
A2:原因是我动态申请时,写的是L=(List)malloc(sizeof(struct List)),改成L=(List)malloc(sizeof(struct LNode))就OK了
2.2 题目2:有序链表合并##
2.2.1设计思路(伪代码)###
定义两个指针p,r
把L1->next赋给p
把L1保存在r中
把r后面的关系断掉
while p&&L2
if p->data<L2->data
p结点插入r后面
p指针往后移
r指针往后移
end if
else if p->data>L2->data
L2结点插入r后面
L2指针往后移
r指针往后移
end if
else
p结点插入r后面
p指针往后移
L2指针往后移
r指针往后移
end if
while p
p中剩余部分插入r中
end while
while L2
L2中剩余部分插入r中
end while
r->next=NULL
end while
2.2.2代码截图###
2.2.3本题PTA提交列表说明###
Q1:输出结果错误
A1:题目要求合后的链表头结点为L1,于是,我直接用L1进行操作,把p,L2直接插在L1上,导致输出结果错误。于是我将L1付给r指针,对r指针进行操作
Q2:如何实现合并两个链表和仍保持有序性
A2:通过遍历两个链表,把较小的数那个插入r中,然后移动较小数所在链表和r的指针,若两个数相同,则只插入其中一个,同时移动p、L2、r的指针,最后,若p或L2有剩余数据,则把剩余的全部插进r中
2.3 题目3:两个有序序列的中位数##
2.3.1设计思路(伪代码)###
主函数
定义链表指针L1,L2
定义n
输入n
函数调用
尾插法建链表函数
定义链表指针s,r
定义i
给L动态申请空间
L赋给r
for i=0 to i<n
给s动态申请空间
输入s->data
把s插到r后面
end for
r->next=NULL
合并链表函数
定义两个指针p,r
把L1->next赋给p
把L1保存在r中
把r后面的关系断掉
if p->data<L2->data
p结点插入r后面
p指针往后移
r指针往后移
end if
else if p->data>=L2->data
L2结点插入r后面
L2指针往后移
r指针往后移
end if
while p
p中剩余部分插入r中
end while
while L2
L2中剩余部分插入r中
end while
r->next=NULL;
找链表的中间数函数
定义指针p
定义n=0,i=0,j
p=L->next;
L=L->next;
while(p)
n++
p指针后移
end while
j=(n+1)/2 //中位数
while(L)
i++
if i==j
输出中位数
end if
L指针后移
end while
2.3.2代码截图###
2.3.3本题PTA提交列表说明###
Q1:做这题时还是比较顺利
A1:要寻找两个有序序列的中位数,先把这两个链表合并,然后遍历合并后的链表,计算出该链表的元素个数,找出中位数是第几个数,再遍历链表找到中位数
3、阅读代码#
3.1 题目##
编写一个程序,找到两个单链表相交的起始节点。
如下面的两个链表:
在节点 c1 开始相交。
3.2 解题思路##
指针 pA 和 pB 分别指向链表 A 和链表 B 的头结点,之后两个指针分别以步幅为 1 的速度向链表的尾部遍历,当指针 pA 遍历到链表 A 的尾节点时,将指针 pA 指向链表 B 的头部。同样地,当指针 pB 遍历到链表 B 的尾节点时,将指针 pB 指向链表 A 的头部。当两个指针相遇时,指针 pA 或者 pB 所指向的节点就是两个链表的相交节点。
3.3 代码截图##
3.4 学习体会##
该题用两个指针相对其他做法,降低了时间复杂度和空间复杂度,也简化了代码,算是最优的解题的方法。
多看题可以开拓我们的思维,打破我们的定向思维,优化算法,找到更高效的解决方法。