《数据结构与算法》——线性表之顺序表(SqList)总结

《数据结构与算法》——线性表之顺序表(SqList)总结

 

从前天开始着手复习线性表部分,整了3个下午才用C++对顺序表的部分内容进行了成功实现,下面就简单进行以下总结。

目录

《数据结构与算法》——线性表之顺序表总结

定义

class SqList

方法实现

错误

难点

参考文献


定义

线性表:具有线性存储结构的抽象数据类型,它是由n个数据元素组成的有限序列。其中数据元素可以是很多种,int、string、char甚至是自定义类型。

课本上还有个定义是说其他几个名词的关系:若干数据项组成了一条记录数据元素),含有大量记录的线性表被称为文件

在书上对抽象数据类型的线性表定义如下图:

 

 

线性表分为顺序表链表,在本文中将对线性表中的顺序表以C++语言的方式,构建SqList类,并对其类方法进行实现。

 

class SqList

 

class SqList {
	private:
		T *data=NULL;//设置成动态的 
		int len,Max;
		int step;
	public:
		SqList(int Max , T t );//{//构造函数, int step = 50 
		void InitList(int Max , T t);//初始化 
		int length();
		int LocateElem(T elem);//按值查找
		T GetElem(int i); //按位查找
		void ListtInsert(int i ,T elem);
		void ListDelete(T elem);//删除元素
		void PrintList(); 
		bool Empty();
		void DestroyList();
		void MergeList(SqList lb);//合并两个表,有序 
		~ SqList();//析构函数 
};

 

方法实现

 

/*编译环境:
win10专业版
DEV C++ 5.11
TDM-GCC 4.9.2 64bit
*/

#include<iostream>
#include<stdlib.h> 
using namespace std;
#define STEP 50
#define OVERFLOW 0

template <typename T >
class SqList {
	private:
		T *data=NULL;//设置成动态的 
		int len,Max;
		int step;
	public:
		SqList(int Max , T t );//{//构造函数, int step = 50 
		void InitList(int Max , T t);//初始化 
		int length();
		int LocateElem(T elem);//按值查找
		T GetElem(int i); //按位查找
		void ListtInsert(int i ,T elem);
		void ListDelete(T elem);//删除元素
		void PrintList(); 
		bool Empty();
		void DestroyList();
		void MergeList(SqList lb);//合并两个表,有序 
		~ SqList();//析构函数 
};

template <typename T > SqList<T>::SqList(int Max , T t){//构造函数, int step = 50
	/*
	* 初始化最大容量,元素类型&错误标记,步长 
	*/
	T *tt = (T*)malloc(sizeof(T)*Max);
	if(!tt){
		cout<<"空间分配失败"<<endl; 
		exit(OVERFLOW);//空间分配失败 
	}
	this->data	= tt;
	this->data[0] = t;
	this->Max  =  Max;
	this->len  =  0;
	this->step =  STEP;
}

template <typename T> void SqList<T>::InitList(int Max , T t){//初始化 
	SqList(Max , t);
}

template <typename T>
int  SqList<T>::length(){//返回顺序表长度 
	return len;
}

template <typename T>
int  SqList<T>::LocateElem(T elem){//按值查找
	int i = 0;
	for( ; i<=this->len && data[i]!= elem;i++);
	if( i <= this->len)
		return i;
	return 0;//无此值 
		 
}

template <typename T>
T    SqList<T>::GetElem(int i){ //按位查找
	if(i<=this->len && i>0 )
		return data[i];
	return data[0]; 
}

template <typename T>
void SqList<T>::ListtInsert(int i ,T elem){//按位插值 
	if (i==0||i>=this->len+2)
		return ;
	if(this->len >= this->Max) {//重新分配内存块 
  		T * Temp = (T *) realloc(this->data, sizeof(T)*(this->Max + this->step));
  		if (Temp == NULL)// {
  			exit(OVERFLOW);//<<"The memory relloced failed!"<<endl; 
		//}
    	this->data = Temp;
		this->Max = this->Max + this->step;
	}
	
	this->len ++;//长度增加 
	int j = this->len ;
	for( ; j>i ;j--){
		this->data[j] = this->data[j-1];
	}
	this->data[j] = elem;
} 

template <typename T>
void SqList<T>::ListDelete(T elem){//删除元素
	int i=0;
	while(i<len && this->data[++i]!=elem);
	if(i==len&&this->data[i]!=elem)
		return ; 
	else{
		while(i<len){
			this->data[i] = this->data[i+1];
			i++;
		}
		this->len--;
	}
}

template <typename T>
void SqList<T>::PrintList(){//输出顺序表 
	cout<<"[";
	if(len==0)
		cout<<" ";
	else{
		for(int i = 1 ; i < len ;i++){
			cout<<this->data[i]<<" ";
		}
		cout<<this->data[len];
	}
	cout<<"]"<<endl;
}

template <typename T>
bool SqList<T>::Empty(){//判空 
	if(this->len==0)
		return 1;
	else 
		return 0; 
}

template <typename T>
void SqList<T>::DestroyList(){//销毁顺序表 
	len=0;
	free(this->data); 
	this->data = NULL;
}

template <typename T>
void SqList<T>::MergeList(SqList<T> lb){//合并两个顺序表
	/*
	*分为两种情况,有序和无序,无序直接合并,有序则按序合并 
	*/
	int i=0,j=0;
	bool flag = 1; 
	while(((++i)<this->len) && (this->data[i] <= this->data[i+1]) );//判断当前字符串是否有序 
	if((i <= this->len) && (this->data[this->len] < this->data[this->len-1]) )//无序 
		flag = 0 ;
	else{
		while(((++j) < lb.len) && (lb.data[j] <= lb.data[j+1]) );//判断合并字符串是否有序 
		if((j == lb.len)  && (lb.data[j] >= lb.data[j-1]) )//有序 
			flag = 1 ;//有序
		else
			flag = 0 ; //无序 
	}
	if(flag){//有序

		T * Temp = (T *) malloc(sizeof(T)*(this->Max));
		int len = this->len,j=1,k=1,l=1;
		if (!Temp)
  			exit(OVERFLOW);
  		while(j<=len)//辅助数组 
		  Temp[j]= this->data[j++];
		
		if(this->Max < this->len + lb.len ){//空间不足 //对A扩充空间 
			T *tem = (T*) realloc(this->data, sizeof(T)*(this->Max + lb.Max));
		if (!tem)
  			//exit(OVERFLOW);
  		this->data = tem ;
  		flag=0; 
		}
		else
			flag = 1;
		//比较大小合并 
		j = 1;
		while(j<=len && k<=lb.len)
			if(Temp[j] <= lb.data[k])
				this->data[l++] = Temp[j++];
			else
				this->data[l++] = lb.data[k++];
		while(j<=len) this->data[l++] = Temp[j++];
		while(k<=lb.len) this->data[l++] = lb.data[k++];
	}
	else{//无序
		T * Temp = (T*) realloc(this->data, sizeof(T)*(this->Max + lb.Max));
		lb.PrintList(); 
		if (!Temp)
  			exit(OVERFLOW);
    	this->data = Temp;
    	j=1;
    	while(j<=lb.len){
    		this->data[len+j] = lb.data[j++];
		}
	}	
	this->Max = flag?this->Max :this->Max + lb.Max;
	this->len = this->len + lb.len;
} 

template <typename T>
SqList<T>::~SqList(){//析构 
	len=0;
	free(this->data); 
	this->data = NULL;
}







int main() {
	
	SqList<int> l(50,-1);
	cout<<"初始化:"; l.PrintList();
	l.ListtInsert(1,6);
	cout<<"在第1位插入6:";l.PrintList();
	l.ListtInsert(2,8);
	cout<<"在第2位插入8:";l.PrintList();
	l.ListtInsert(2,7);
	cout<<"在第2位插入7:";l.PrintList();
	l.ListtInsert(4,9);l.ListtInsert(1,5);
	l.ListtInsert(1,4);l.ListtInsert(1,3);
	l.ListtInsert(1,2);l.ListtInsert(1,1);
	cout<<"在插入很多数据后:";l.PrintList();
	cout<<"当前表长度为:"<<l.length()<<endl; 
	l.ListDelete(4);
	cout<<"删除元素4:"; l.PrintList();
	cout<<"查询第6个元素是:"<<l.GetElem(6)<<endl;
	cout<<"查询元素6的位置为:"<<l.LocateElem(6)<<endl;

	//新建一个顺序表
	SqList<int> l2(50,-1);
	l2.ListtInsert(1,6);l2.ListtInsert(1,5);l2.ListtInsert(1,4);
	l2.ListtInsert(1,3);l2.ListtInsert(1,2);l2.ListtInsert(1,1);
	cout<<"l2有序初始化:"; l2.PrintList();
	l.MergeList(l2);
	cout<<"l与l2合并结果:"; l.PrintList();

	//新建一个顺序表
	SqList<int> l3(50,-1);
	l3.ListtInsert(1,9);l3.ListtInsert(1,8);l3.ListtInsert(1,5);
	l3.ListtInsert(1,7);l3.ListtInsert(1,4);l3.ListtInsert(1,2);
	cout<<"l3无序初始化:"; l3.PrintList();
	l.MergeList(l3);
	cout<<"l与l3合并结果:"; l.PrintList();
	l3.DestroyList();
	cout<<"销毁l3:"; l3.PrintList();
	return 0;
}

 

错误

在代码实现的过程中,采用了模板类+外联函数的方式,主要是为了达到C++和数据结构同时复习的目的。但在过程中以下代码总是报错:

template <typename T , int step=50 >
class SqList {
	private:
		T *data=NULL;//设置成动态的 
		int len,Max;
		int step;
	public:
		SqList(int Max , T t );//{//构造函数, int step = 50 
		......

};
template <typename T,int step = 50  > SqList<T>::SqList(int Max , T t){//构造函数, int step = 50
	T *tt = (T*)malloc(sizeof(T)*Max);
	if(!tt){
		cout<<"空间分配失败"<<endl; 
		exit(OVERFLOW);//空间分配失败 
	}
	this->data	= tt;
	this->data[0] = t;
	this->Max  =  Max;
	this->len  =  0;
	this->step =  step;
}
//错误:
/* [Error] invalid use of incomplete type 'class SqList<T>'
*[Error] declaration of 'class SqList<T>'
*原因? 
*/

将其改为内联函数错误便消失,但是就想用外联函数,找原因也不知个所以然,所以就将其中的默认参数给删掉了,解决了问题。如下:

 

template <typename T >
class SqList {
	private:
		T *data=NULL;//设置成动态的 
		int len,Max;
		int step;
	public:
		SqList(int Max , T t );//{//构造函数, int step = 50 
		......

};

template <typename T> SqList<T>::SqList(int Max , T t){//构造函数, int step = 50
	T *tt = (T*)malloc(sizeof(T)*Max);
	if(!tt){
		cout<<"空间分配失败"<<endl; 
		exit(OVERFLOW);//空间分配失败 
	}
	this->data	= tt;
	this->data[0] = t;
	this->Max  =  Max;
	this->len  =  0;
	this->step =  STEP;//宏定义STEP
}

 

难点

对于“数据结构”这一部分学习的难点,我认为一是对实际问题进行抽象化处理,二是对数据结构实现时的不熟练,这部分应归结于语言和编程能力的不足

参考文献

严蔚敏,吴伟民. 数据结构(C语言版)[M]. 北京: 清华大学出版社,2013.

 

如有错误,还请朋友不吝指正。

©️2020 CSDN 皮肤主题: 书香水墨 设计师: CSDN官方博客 返回首页
实付0元
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值