第一范文网 - 专业文章范例文档资料分享平台

中南大学数据结构与算法第10章内部排序课后作业答案

来源:用户分享 时间:2025/5/24 0:34:25 本文由loading 分享 下载这篇文档手机版
说明:文章内容仅供预览,部分内容可能不全,需要完整文档或者需要复制内容,请下载word后使用。下载word有问题请添加微信号:xxxxxxx或QQ:xxxxxx 处理(尽可能给您提供完整文档),感谢您的支持与谅解。

┌──┐ 0│ ∧ │ ├──┤

1│ → 0.13→0.16→ ∧ ├──┤

2│ →0.20→ ∧ ├──┤ 3│ →0.39→ ∧ ├──┤

4│ →0.42→ ∧ ├──┤

5│ →0.53→ ∧ ├──┤

6│ →0.64→ ∧ ├──┤

7│ →0.71→0.79→ ∧ ├──┤

8│ →0.89→ ∧ ├──┤ 9│ ∧ │ └──┘

结果为:0.13 0.16 0.20 0.39 0.42 0.53 0.64 0.71 0.79 0.89

11.若关键字是非负整数、快速排序、归并、堆和基数排序啊一个最快?若要求辅助空间为O(1),则应选择谁? 若要求排序是稳定的,且关键字是实数,则应选择谁? 答:

若关键字是非负整数,则基数排序最快;若要求辅助空间为O(1),则应选堆排序;若要求排序是稳定的,且关键字是实数,则应选归并排序,因为基数排序不适用于实数,虽然它也是稳定的。

12.对于8.7节的表8.2,解释下述问题:

(1)当待排序的关键字序列的初始态分别为正序和反序时,为什么直接选择排序的时间基本相同?若采用本书8.4.1节的算法,这两种情况下的排序时间是否基本相同?

(2)为什么数组的初态为正序时,冒泡和直接插入排序的执行时间最少?

(3)若采用8.3.2节的快速排序,则数组初态为正序和反序时,能得到与表8.2类似的结果吗? 答:

(1)由于在直接选择排序中,主要的操作是比较操作和移动操作。无论文件的初始状态如何,若文件有n个记录,则都要进行n-1趟直接选择排序,第i趟直接选择排序中都要做n-i次比较才能选出最小关键字的记录。所以总的比较次数都为O(n2)。至于记录的移动次数,初始文件为正序时,移动次数为0,当文件初始时为反序,总的移动次数为3(n-1)。因此当待排序的关键字序列的初始态分别为正序和反序时,直接选择排序的时间基本相同,为O(n2)。若采用本书8.4.1节的算法,这两种情况下的排序时间基本相同。

(2)当冒泡排序是正序时,只需做一趟冒泡排序就可完成,共做n-1次比较,移动次数为0,所以执行时间最少。而直接插入排序时,若初始为正序,则做了n-1趟直接插入排序,但每趟排序只做了一次比较,共做n-1次比较。移动次数为0。所以当数组初态为正序,直接插入排序时间也最少。

(3)不能,其中辅助空间不同

13. 将哨兵放在R[n]中,被排序的记录放在R[0..n-1]中,重写直接插入排序算法。 解:

重写的算法如下: void InsertSort(SeqList R)

{//对顺序表中记录R[0..n-1]按递增序进行插入排序 int i,j;

for(i=n-2;i>=0;i--) //在有序区中依次插入R[n-2]..R[0] if(R[i].key>R[i+1].key) //若不是这样则R[i]原位不动 {

R[n]=R[i];j=i+1; //R[n]是哨兵

do{ //从左向右在有序区中查找插入位置

R[j-1]=R[j]; //将关键字小于R[i].key的记录向右移 j++;

}while(R[j].key

R[j-1]=R[n]; //将R[i]插入到正确位置上 }//endif }//InsertSort.

14.以单链表作为存储结构实现直接插入排序算法。 解:

#define int KeyType //定义KeyType 为int型 typedef struct node{

KeyType key; //关键字域

OtherInfoType info; //其它信息域, struct node * next; //链表中指针域 }RecNode; //记录结点类型

typedef RecNode * LinkList ; //单链表用LinkList表示

void InsertSort(LinkList head)

{//链式存储结构的直接插入排序算法,head是带头结点的单链表 RecNode *p,*q,*s;

if ((head->next)&&(head->next->next))//当表中含有结点数大于1 {

p=head->next->next;//p指向第二个节点 head->next=NULL;

q=head;//指向插入位置的前驱节点

while(p)&&(q->next)&&(p->keynext->key) q=q->next; if (p)

{s=p;p=p->next;// 将要插入结点摘下

s->next=q->next;//插入合适位置:q结点后 q->next=s; } } }

15.设计一算法,使得在尽可能少的时间内重排数组,将所有取负值的关键字放在所有取非负值的关键字之前。请分析算法的时间复杂度。 解:

因为只需将负数关键字排在前面而无需进行精确排列顺序,因此本算法采用两端扫描的方法,就象快速排序采用的方法一样,左边扫描到正数时停止,开始扫描右边,遇到负数时与左边的当前记录交换,如此交替进行,一趟下来就可以完成排序。

void ReSort(SeqList R)

{//重排数组,使负值关键字在前 int i=1,j=n; //数组存放在R[1..n]中 while (i

{ while(i

R[0]=R[i]; //R[0]为辅助空间

while(i=0)// 遇到正数则继续向左扫描 j--;

R[i++]=R[j];R[j--]=R[0];//交换当前两个元素并移动指针 }//endwhile }//ReSort

本算法在任何情况下的比较次数均为n(每个元素和0)相比,交换次数少于n/2,总的来说,时间复杂度为O(n).

中南大学数据结构与算法第10章内部排序课后作业答案.doc 将本文的Word文档下载到电脑,方便复制、编辑、收藏和打印
本文链接:https://www.diyifanwen.net/c3jjpy4e9d65zpak1bu5i_3.html(转载请注明文章来源)
热门推荐
Copyright © 2012-2023 第一范文网 版权所有 免责声明 | 联系我们
声明 :本网站尊重并保护知识产权,根据《信息网络传播权保护条例》,如果我们转载的作品侵犯了您的权利,请在一个月内通知我们,我们会及时删除。
客服QQ:xxxxxx 邮箱:xxxxxx@qq.com
渝ICP备2023013149号
Top