数据结构与算法参考答案(第二周)
一、设顺序表va中的数据元素递增有序。试写一算法,将x插入到顺序表的适当位置上,以保持该表的有序性。
答:
分析题目可知,我们需要先查到x需要在顺序表va中插入的位置。假设我们插入在顺序表中的位置为va.elem[i+1]。这里我们需要满足x的值大于等于va.elem[i]且小于va.elem[i+1]。之后我们需要将顺序表的va.length - i - 1个元素后移一位。最后将表长va.length加1。
本算法实现的伪代码如下:
/* 函数名称:单调顺序表插入算法 传入参数:需要插入的线性表va, 需要插入的元素x 返回值:返回OK代表插入成功,返回OVERFLOW代表以及达到最大长度,无法继续插入 */ Status InsertOrderList(SqList &va, ElemType x) { if(va.length == va.listsize) { return OVERFLOW; } else { int i; //查找x所处在的位置 for(i = va.length - 1; i >= 0; --i) { if(x >= va.elem[i]) { break; } } //实现元素后移 for(int j = va.length - 1; j >= i + 1; --j) { va.elem[j + 1] = va.elem[j]; } va.elem[i + 1] = x; //插入x va.length++; //表长+1 return OK; } } |
算法分析:本算法的时间复杂度为O(n)。占用的空间依旧是开辟的那个线性表大小的空间。算法执行效率较好,同时引入了对表的最大长度的判定可以避免出现数据溢出的情况。
二、设A = (a1,...,am)和B = (b1,...,bn)均为顺序表,A`和B`分别为A和B中除去最大共同前缀后的子表(例如,A = (x, y, y, z, x, z),B = (x, y, y, z, y, x, x, z),则两者中最大的共同前缀为(x, y, y, z),在两表中除去最大共同前缀后的子表分别为A` = (x, z)和B` = (y, x, x, z)。若A` = B` = 空表,则A = B;若A` = 空表,而B` ≠ 空表,或者两者均不为空表,且A`的首元小于B`的首元,则A < B;否则A > B。试写一个比较A, B大小的算法(请注意:在算法中,不要破坏原表A和B,并且,也不一定先求得A`和B`才进行比较)。
答:
分析题目,我们可以知道需要对特殊情况进行判定。在有空表存在的情况通过条件判断语句进行判断。如果两个表都是非空。我们通过一个下标按照从头到尾依次进行遍历,当两表相同下标元素遇到出现不等关系时,我们即可根据这两个元素的大小关系判断出两表的大小关系。需要注意的是,我们在遍历的时候取得是两表中最短的length作为遍历的最大长度。在这种情况下,当我们在遍历时每个元素都相等。我们可以认为较长表大于较短表了。
综上分析,该题的算法实现伪代码如下:
/* 函数名称:比较两线性表的算法 传入参数:需要比较的线性表A,B 返回值:返回BIGGER代表A比B大,返回SMALLER代表A比B小,返回EQUAL代表A,B大小相等 */ Status CompareOrderList(SqList &A, SqList &B) { int length = min(A.length, B.length) //length长度为A,B中的最小值 int temp = 0; //设置临时状态判定变量 //如果A的长度大于Btemp为1,小于为-1,相等仍为0 temp = (A.length > B.length) ? 1 : -1; if(A.length != 0 && B.length == 0) { //A不为空B为空 A大于B return BIGGER; } else if(A.length == 0 && B.length != 0){//B不为空A为空 A小于B return SMALLER; } else if(A.length == 0 && B.length == 0{//A,B均为空,A = B return EQUAL; } else{ for(int i = 0; i < length; ++i) { if(A.elem[i] > B.elem[i]) { //如果出现A的元素大于B的元素直接返回BIGGER return BIGGER; } else if(A.elem[i] < B.elem[i]) { //如果出现B的元素大于A的元素直接返回SMALLER; return SMALLER; } } //当执行完后肯定是A或B在去除相同前缀必定至少有一个字串为0的情况 if(temp == 0) { //去除后最终都为空表 return EQUAL; } else if(temp == 1){ //去除后只剩A表 return BIGGER; } else { //去除后只剩B表 return SMALLER; } } } |
算法分析:该算法增加许多条件的特判,增强了算法的健壮性。同时,该算法的时间复杂度为O(n)是比较理想的比较算法。空间占用也只是两个线性表的本来的储存空间。总的来说,这个算法是一个解决这种问题比较好的算法。