第二章线性表的顺序表练习题
1、从顺序表中删除具有最小值的元素(假设唯一) 并由函数返回被删元素的值。空出的位置由最后一个元素填补,若顺序表为空,则显示出错信息并退出运行。
算法思想:搜索整个顺序表,查找最小值元素并记住其位置,搜索结束后用最后一个元素填补空出的原最小值元素的位置。
bool Del_Min(SeqList &L,int &value){
//删除顺序表L中最小值元素节点,并通过引用型参数value返回其值
//若删除成功,则返回true,否则返回false
if(L.length==0){
return false; //表空,中止操作返回
}
int value=L.data[0];
int pos=0; //假定0号元素的值最小
for(int i=1;i<L.length;i++){ //循环,寻找具有最小值的元素
if(L.data[i]<value){ //让value记忆当前具有最小值的元素
value=L.data[i];
pos=i;
}
}
L.data[pos]=L.data[L.length-1]; //空出的位置由最后一个元素填补
L.length--;
return true; //此时,value即为最小值
}
2、设计一个高效算法,将顺序表L的所有元素逆置,要求算法的空间复杂度为0(1)。
算法思想:扫描顺序表L的前半部分元素,对于元素L.data[i] (0<=i<L.length/2)将其与后半部分的对应元素L.data[L.length-i-1] 进行交换。
void Reverse(SeqList &L){
int temp=0; //辅助变量
for(int i=0;i<L.length/2;i++){
temp=L.data[i]; //交换L.data[i]与L.data[L.length-i-1]
L.data[i]=L.data[L.length-i-1];
L.data[L.length-i-1]=temp;
}
}
3、对长度为n的顺序表L,编写一个时间复杂度为O(n)、空间复杂度为0(1)的算法,该算法删除线性表中所有值为x的数据元素。
算法思想:记录顺序表L中不等于x的元素个数(即需要保存的元素个数),扫描时将不等于x的元素移动到下标k的位置,并更新k值。扫描结束后修改L的长度。
void Del_x_1(SeqList &L,int x){
//本算法实现删除顺序表L中所有值为x的数据元素
int k=0; //k记录值等于x的元素个数
for(int i=0;i<L.length;i++){
if(L.data[i]!=x){
L.data[k]=L.data[i];
k++; //不等于x的个数加1
}
}
L.length=k; //顺序表L的长度递减
}
4、从有序顺序表中删除其值在给定值s与t之间(要求s<t)的所有元素,若s或t不合理或顺序表为空,则显示出错信息并退出运行。
在很多教材中(包括本书)指的“有序”,如无特别说明,通常是指“递增有序”。注意本题与上题的区别,因为是有序表,所以删除的元素必然是相连的整体。
算法思想: 先寻找值大于或等于s的第一个元素(第一个删除的元素),然后寻找值大于t的第一一个元素(最后一个删除的元素的下一个元素),要将这段元素删除,只需直接将后面的元素前移。
void Del_s_2(SeqList &L,double s,double t){
//删除有序顺序表L中值在给定值s和t之间的所有元素
if(s>=t||L.length==0){ //判定s的值不能大于t,且顺序表不能为空,否则,返回false
return;
}
int i,j;
for(i=0;i<L.length&&L.data[i]<s;i++); //寻找值最大于或等于s的第一个元素
if(i>=L.length){ //所有元素值均小于s,且L长度等于或者大于i,返回
return ;
}