线性表的顺序表示和实现(数据结构课本2.2节)

线性表的基本功能通过函数总结(综合数据结构课本2.2的伪代码)

相比较前两个线性表博客增加:

           1>结构体实现顺序表指针,长度,空间大小定义,避免了多函数的混乱使用,简化了代码。

           2>运用了realloc函数,避免了插入时动态空间不够的问题。

其余函数功能前边均已经实现。

#include <iostream>
#include <stdio.h>
#include <stdlib.h>
#include <malloc.h>
#define OK 1
#define TRUE 1
#define ERROR 0
#define FALSE 0
#define LIST_INIT_SIZE 100 
#define LISTINCREMENT 10 
typedef int Status;
typedef Status ElemType;
typedef ElemType * List;
typedef struct{
	ElemType *elem;
	int length;
	int listsize;
}SqList; 
/* run this program using the console pauser or add your own getch, system("pause") or input loop */
Status InitList(SqList &L);
Status ListInsert(SqList &L,ElemType i,ElemType e);
Status ListDelete(SqList &L,ElemType i);
Status equal(ElemType a,ElemType b);
Status LocateElem_Sq(SqList L,ElemType e,Status (*equal)(ElemType,ElemType));
void MergeList(SqList L1,SqList L2,SqList &L3);
Status DestroyList(SqList &L);

int main(int argc, char *argv[]) {
	SqList L1;
	SqList L2;
	SqList L3;
	Status i,m,s,u; 
	if(InitList(L1)){
	List a1=L1.elem;
	printf("请输入线性表L1待输入元素的个数:");
	scanf("%d",&s); 
	printf("请输入线性表1的元素:");
		for(i=0;i<s;i++){
			scanf("%d",(a1+i));
		}
	}
	L1.length=s;
	//测试:ListInsert函数; 
	printf("\n");
	printf("测试:在L1表的第三个元素前插入5;\n"); 
    if(ListInsert(L1,3,5)){
	    printf("请输出插入后的队列:\n");
		for(i=0;i<L1.length;i++){
		printf(" %d ",L1.elem[i]);
		} 
	}
	
   	//测试:LocateElem_Sq函数;
	printf("\n");
	printf("测试:寻找L1表中与元素5相等元素的位置;\n");
	i=LocateElem_Sq(L1,5,equal);
	if(i!=0){
		printf("元素5的位置是:%d\n",i); 
	}else{
		printf("未找到元素5;\n"); 
	} 
	
	//测试:ListDelete函数;
	printf("\n");
	printf("测试:删除L1表的第三个元素;\n");
	if(ListDelete(L1,3)){
	    printf("请输出删除后的队列:\n");
		for(i=0;i<L1.length;i++){
		printf(" %d ",L1.elem[i]);
		} 
	} 
	printf("\n"); 

	if(InitList(L2)){
	List a2=L2.elem;
	printf("请输入线性表L2待输入元素的个数:");
	scanf("%d",&u);
	printf("请输入线性表2的元素:");
		for(i=0;i<u;i++){
			scanf("%d",(a2+i));
		}
	}
	L2.length=u;
	printf("\n");

	MergeList(L1,L2,L3);
	printf("请输出归并后L3的元素序列:"); 
	for(i=0;i<L3.length;i++){
		printf(" %d ",L3.elem[i]);
	}
	printf("\n");
	 
	 
	 
	if(DestroyList(L1)){
			printf("线性表L1已经销毁;\n"); 
		}
	if(DestroyList(L2)){
			printf("线性表L2已经销毁;\n"); 
		}
	if(DestroyList(L3)){
			printf("线性表L3已经销毁;\n"); 
		}
	
	return 0;
}
 
Status InitList(SqList &L){
	L.elem=(ElemType*)malloc(sizeof(ElemType)*LIST_INIT_SIZE);
	if(L.elem==NULL){
		printf("动态内存申请失败;");
	}else{
		L.length=0;
		L.listsize=100;
	}
	return OK;
}

Status ListInsert(SqList &L,ElemType i,ElemType e){          //在L的第i个元素前插入元素e 
	if(i<1||i>L.length+1)    return ERROR;
	if(L.length>=L.listsize){
		List newbase=(ElemType*)realloc(L.elem,sizeof(ElemType)*(L.listsize+LISTINCREMENT));
		if(newbase==NULL){
		printf("动态内存申请失败;");
		}else{
			L.elem=newbase;
			L.listsize+=LISTINCREMENT;
		}
	}
	ElemType j;
	for(j=L.length;j>=i;--j){             //这里的插入内存数据转换用的都是赋值,下边删除直接用的地址 
		*(L.elem+j)=*(L.elem+j-1); 
	}
	*(L.elem+i-1)=e;
	++L.length;
	return OK;
}

Status ListDelete(SqList &L,ElemType i){          //删除L的第i个元素 
	List j;
	j=&(L.elem[i-1]);
	for(;j<&(L.elem[L.length-1]);++j){
		*j=*(j+1);
	}
	--L.length;
	return OK;
}

Status equal(ElemType a,ElemType b){
	if(a==b){
		return OK;
	}else{
		return ERROR;
	}
}
Status LocateElem_Sq(SqList L,ElemType e,Status (*equal)(ElemType,ElemType)){        //判断表中是否有与元素e相同的元素 
    Status i=1;
	while(i<=L.length&&!(*equal)(L.elem[i-1],e)){
		i++;
	}	
	if(i<=L.length){
		return i; 
	}else{
		return 0;
	}
}




void MergeList(SqList L1,SqList L2,SqList &L3){                   //顺序表的归并 
	List a,b,c,a_Last,b_Last;
	a=L1.elem;
	b=L2.elem;
	L3.listsize=L3.length=L1.length+L2.length;
	L3.elem=(ElemType *)malloc(sizeof(ElemType)*(L3.listsize));
	a_Last=a+L1.length-1;
	b_Last=b+L2.length-1;
	c=L3.elem;
	Status i=0;
	while(a<=a_Last&&b<=b_Last){
		if(*a<=*b){
			*(c++)=*a++;
		}else{
			*(c++)=*b++;
		}
	//	i++;         开始用*(c+i)是不对的,因为指针在移动,第一次左移一个第二次是在第一次的基础上移动的。 
	}
	while(a<=a_Last) *(c++)=*(a++);
    while(b<=b_Last) *(c++)=*(b++);
}

Status DestroyList(SqList &L){                   //申请的动态空间释放 
	free(L.elem);
	L.elem=NULL;
	return OK;
}

运行结果:

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值