题目
删除线性表中所有值为 的元素。
方法一
用 记录顺序表中不等于 的元素的个数,扫描顺序表 ,若当前元素不等于 ,则将当前元素移动到 位置,若当前元素等于 ,不做任何处理。
void del_x_1(SqList &L, ElemType x){
int k = 0;
for(int i=0; i<L.length; i++){
if(L.data[i] != x){
L.data[k] = L.data[i];
k++;
}
}
L.length = k;
}
方法二
用 记录顺序表中等于 的元素的个数,顺序扫描 ,若当前元素等于 ,则 ,若当前元素不等于 ,则将当前元素前移 位。
void del_x_2(SqList &L, ElemType x){
int k = 0;
for(int i=0; i<L.length; i++){
if(L.data[i] == x)
k++;
else
L.data[i-k] = L.data[i];
}
L.length = L.length - k;
}
方法三
设置头尾两个指针(i = 1, j = n)
,从两端向中间移动,反遇到最左端值x
的元素时,直接将最右端非x
的元素移至这个位置,当右端指针遇到值x
的元素时,直接忽略这个元素,指针继续前移,最后当两指针相遇时循环结束,指针以后的部分都被删除,指针的值即为顺序表长度。这个方法的缺点就是会改变表中元素的相对位置。
void del_x_3(SqList &L, ElemType x){
int head = 1, tail = L.length;
while(head != tail){
while(L.data[tail-1] == x && head != tail){
tail--;
}
if(L.data[head-1] == x){
L.data[head-1] = L.data[tail-1];
tail = tail-1;
}
head++;
}
L.length = head;
}
总结
- 方法一和方法二是两个·互逆思路,遍历整个顺序表,其时间复杂度为 ,这两个方法便于理解,方法三平均只需遍历半个顺序表,在性能上更优,但确定就是改变了原顺序表元素的相对位置,对于无序要求的情况下,方法三时首选;
- 三种方法的空间复杂度均为 。