有序表删除重复元素

题目

从有序表中删除所有其值重复的元素,使表中所有的元素的值均有不同

算法设计

解法一

用类似于直接插入排序的思想,初试时将第一个元素视为非重复的有序表,之后依次判断后面的元素是否与前面的非重复元素有序表的最后一个元素相同,若相同则继续向后判断,若不同则插入前面的非重复有序表的,最后直至判断到表尾为止

bool del(sqlist &L)
{
	if(L.length==0)
    	return false;
    int i,j;//i存储第一个不相同的元素,j为工作指针
	for(i=0,j=1;j<L.length;j++)
	    if(L.data[i]!=L.data[j])//查找下一个与上个元素不同的元素
	        L.data[++i]=L.data[j];//找到后,将元素前移
        L.length=i+1;
        return true;
}

解法二

每遇到一个重复的就将后面的整体向前移动一个,以此类推

bool Delete_Same(SqList &L)
{
	for(int i=0;i<L.length;i++)
	{
		int k=0;
		for(int j=i+1;j<L.length;j++)
		{
			if (L.data[i] == L.data[j])
				k++;	
			else
				L.data[j-k]=L.data[j];
		}
		L.length=L.length-k;
	}
	return true;
}

实验

整体实验如下:

#include <iostream>
#include <cstdio>
using namespace std;

typedef struct
{
    int  *data;
    int Maxsize=10,length;
}sqlist;

void init(sqlist &L)//初始化 
{
    for(int i=0;i<L.Maxsize;i++)
        L.data[i]=0;
    L.length=0;
}
bool create(sqlist &L)//创建 
{
    for(int i=0;i<L.Maxsize;i++)
    {
        cin>>L.data[i];
        L.length++;
    }
    return true;
}
int print(sqlist &L)//打印 
{
    for(int i=0;i<L.length;i++)
        cout<<L.data[i]<<" ";
    printf("\n");
    return true;
}
bool del(sqlist &L)//删除重复元素 
{
/*bool Delete_Same(SqList &L)
{
	for(int i=0;i<L.length;i++)
	{
		int k=0;
		for(int j=i+1;j<L.length;j++)
		{
			if (L.data[i] == L.data[j])
				k++;	
			else
				L.data[j-k]=L.data[j];
		}
		L.length=L.length-k;
	}
	return true;
}*/

	if(L.length==0)
    	return false;
    int i,j;
	for(i=0,j=1;j<L.length;j++)
	    if(L.data[i]!=L.data[j])
	        L.data[++i]=L.data[j];
        L.length=i+1;
        return true;
}
	
int main()
{
    sqlist L;
    init(L);
    create(L);
    //print(L);
    del(L);
    print(L);
    cout<<"length = "<<L.length<<endl;
}

结果

如下:
在这里插入图片描述

此题本想设一个k来计数,作为重复的元素,每遇到一个重复的元素就前移k个,但是忽略了向前移动后,留在原地的元素其实又和元素自己向前移动后的位置元素重复了,造成k计数不准,然后就只能没遇到一个元素就将后面所有的元素都向前移一个(解法二),不知道有没有大佬能解决我遇到的问题,每遇到一个都前移的话,效率不够高。

  • 5
    点赞
  • 17
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值