2-1-2顺序表的源码

2-1-2顺序表的源码

c1.h

// c1.h (程序名)
#pragma once

#ifndef __C1_H__
#define __C1_H__
#include<string.h>
#include<ctype.h>
#include<malloc.h> // malloc()等
#include<limits.h> // INT_MAX等
#include<stdio.h> // EOF(=^Z或F6),NULL
#include<stdlib.h> // atoi()
#include<io.h> // eof()
#include<math.h> // floor(),ceil(),abs()
#include<process.h> // exit()
#include<iostream> // cout,cin
using namespace std;
// 函数结果状态代码
#define TRUE 1
#define FALSE 0
#define SUCCEEDED 1
#define ERROR 0
#define FAILED 0
#define INFEASIBLE -1
#define EQUAL 1
#define UNEQUAL 0
// #define OVERFLOW -2 因为在math.h中已定义OVERFLOW的值为3,故去掉此行
typedef int Status; // Status是函数的类型,其值是函数结果状态代码,如SUCCEEDED等
typedef int Boolean; // Boolean是布尔类型,其值是TRUE或FALSE

#endif

Compare.cpp

// Compare.cpp 几个常用的函数
#include "Compare.h"
#include "SqListType.h"
#include <stdio.h>

Status equal(ElemType c1,ElemType c2)
{ // 判断是否相等的函数
	if(c1==c2)
		return EQUAL;
	else
		return UNEQUAL;
}

int unequal(ElemType a,ElemType b)
{ // 根据a<、=或>b,分别返回-1、0或1
	if(a==b)
		return 0;
	else
		return (a-b)/abs(a-b);
}

void Dprint(ElemType c)
{
	printf("%d ",c);
}

void Cprint(ElemType c)
{
	printf("%c ",c);
}

void CitePrint(ElemType &c)
{
	printf("%d ",c);
}

Compare.h

#pragma once

#ifndef	__COMPARE_H__
#define __COMPARE_H__

#include "c1.h"
#include "SqListType.h"

// 判断是否相等的函数
Status equal(ElemType c1,ElemType c2);

// 根据 a<、 =或 >b,分别返回 -1、 0或 1
int unequal(ElemType a,ElemType b);

void Dprint(ElemType c);

void Cprint(ElemType c);

void CitePrint(ElemType &c);


#endif

SqListBasicOperation.cpp

// bo2-1.cpp 顺序表示的线性表(存储结构由c2-1.h定义)的基本操作(12个),包括算法2.3,2.4,2.5,2.6
#include "c1.h"
#include "SqListType.h"
#include "SqListBasicOperation.h"

void InitList(SqList &L) // 算法2.3
{ // 操作结果:构造一个空的顺序线性表L
	L.elem=(ElemType*)malloc(LIST_INIT_SIZE*sizeof(ElemType));
//	printf("!L.elem=%x\n",!L.elem);
	if(L.elem==NULL)
		exit(OVERFLOW); // 存储分配失败
	if (L.elem!=NULL){
		L.length=0; // 空表长度为0
		L.listsize=LIST_INIT_SIZE; // 初始存储容量
	}

}

void DestroyList(SqList &L)
{ // 初始条件:顺序线性表L已存在。操作结果:销毁顺序线性表L
	free(L.elem);
	L.elem=NULL;
	L.length=0;
	L.listsize=0;
}

void ClearList(SqList &L)
{ // 初始条件:顺序线性表L已存在。操作结果:将L重置为空表
	L.length=0;
}

Status ListEmpty(SqList L)
{ // 初始条件:顺序线性表L已存在。操作结果:若L为空表,则返回TRUE,否则返回FALSE
	if(L.length==0)
		return TRUE;
	else
		return FALSE;
}

int ListLength(SqList L)
{ // 初始条件:顺序线性表L已存在。操作结果:返回L中数据元素个数
	return L.length;
}

Status GetElem(SqList L,int pos,ElemType &e)
{ // 初始条件:顺序线性表L已存在,1≤pos≤ListLength(L)。操作结果:用e返回L中第i个数据元素的值
	if(pos<1||pos>L.length)
		return ERROR;
	else
		e=*(L.elem+pos-1);
	return SUCCEEDED;
}

int LocateElem(SqList L,ElemType e,Status(*compare)(ElemType,ElemType))
{ // 初始条件:顺序线性表L已存在,compare()是数据元素判定函数(满足为1,否则为0)
	// 操作结果:返回L中第1个与e满足关系compare()的数据元素的位序。
	//           若这样的数据元素不存在,则返回值为0。算法2.6
	ElemType *p;
	int pos=1; // i的初值为第1个元素的位序
	p=L.elem; // p的初值为第1个元素的存储位置
//	printf("p=L.elem地址是%x\n",p);
//	printf("原始pos=%d\n",pos);
//	printf("*****************\n");
	while(pos<=L.length){
		  if (compare(*p,e)==UNEQUAL){
			  p++;
			  pos++;
//			  printf("地址=%x\n",p);
//			  printf("++pos=%d\n",pos);
		  }else{
			  break;
		  }
	}
	if(pos<=L.length)
		return pos;
	else
		return FAILED;
}

Status PriorElem(SqList L,ElemType cur_e,ElemType &pre_e)
{ // 初始条件:顺序线性表L已存在
	// 操作结果:若cur_e是L的数据元素,且不是第一个,则用pre_e返回它的前驱,
	//           否则操作失败,pre_e无定义
	int pos=1;
	ElemType *p=L.elem;
	if (*L.elem==cur_e){
		return INFEASIBLE;
	}
	pos+=1;
	p=L.elem+1;
	while(pos<=L.length&&*p!=cur_e)
	{
		p++;
		pos++;
	}
	if(pos>L.length)
		return INFEASIBLE; // 操作失败
	else
	{
		pre_e=*--p;
		return SUCCEEDED;
	}
}

Status NextElem(SqList L,ElemType cur_e,ElemType &next_e)
{ // 初始条件:顺序线性表L已存在
	// 操作结果:若cur_e是L的数据元素,且不是最后一个,则用next_e返回它的后继,
	//           否则操作失败,next_e无定义
	int pos=1;
	ElemType *p=L.elem;
	while(pos<L.length&&*p!=cur_e)
	{
		pos++;
		p++;
	}
	if(pos==L.length||pos>L.length)
		return INFEASIBLE; // 操作失败
	else
	{
		next_e=*++p;
		return SUCCEEDED;
	}
}

Status ListInsert(SqList &L,int pos,ElemType e) // 算法2.4
{ // 初始条件:顺序线性表L已存在,1≤pos≤ListLength(L)+1
	// 操作结果:在L中第pos个位置之前插入新的数据元素e,L的长度加1
	ElemType *newbase,*insert,*an;
	if(pos<1||pos>L.length+1) {
		return ERROR;//pos值不合法
	}else{
		if(L.length>=L.listsize) // 当前存储空间已满,增加分配
		{	
			newbase=(ElemType *)realloc(L.elem,(L.listsize+LIST_INCREMENT)*sizeof(ElemType));
//			printf("旧的L.elem=%x\n",L.elem);
//			printf("新的newbase=%x\n",newbase);
//			printf("L的长度=%d",sizeof(L));
			if(newbase==NULL)
				exit(OVERFLOW); // 存储分配失败
			L.elem=newbase; // 新基址
//			printf("新的L.elem=%x\n",L.elem);
			L.listsize+=LIST_INCREMENT; // 增加存储容量
		}
		insert=L.elem+pos-1; // insert为插入位置
		for(an=L.elem+L.length-1;an>=insert;--an) // 插入位置及之后的元素右移
			*(an+1)=*an;
		*insert=e; // 插入e
		++L.length; // 表长增1
		return SUCCEEDED;
	}

}

Status ListDelete(SqList &L,int pos,ElemType &e) // 算法2.5
{ // 初始条件:顺序线性表L已存在,1≤pos≤ListLength(L)
	// 操作结果:删除L的第i个数据元素,并用e返回其值,L的长度减1
	ElemType *delP,*an,*mov;
	if(pos<1||pos>L.length){		// pos值不合法
		return ERROR;
	}else{
		delP=L.elem+pos-1; // delP为被删除元素的位置
		e=*delP; // 被删除元素的值赋给e
		an=L.elem+L.length-1; // 表尾元素的位置
		mov=++delP;//pos位置上的指针向后移动一位,为移动pos后面的元素做准备
		while(mov<=an){
			*(mov-1)=*mov;
			++mov;// 被删除元素之后的元素左移
		}

		L.length--; // 表长减1
		return SUCCEEDED;
	}
}

void ListTraverse(SqList L,void(*vi)(ElemType&))
{ // 初始条件:顺序线性表L已存在
	// 操作结果:依次对L的每个数据元素调用函数vi()
	//           vi()的形参加'&',表明可通过调用vi()改变元素的值
	ElemType *p;//p是从顺序表开始遍历到表结束的指针
	int i;
	p=L.elem;
	for(i=1;i<=L.length;i++){
			vi(*p);//vi是显示格式的函数指针
			p++;
	}
	printf("\n");
}

SqListBasicOperation.h

#pragma	once

#ifndef _SQLISTBASICOPERATION_H__
#define _SQLISTBASICOPERATION_H__

#include "c1.h"
#include "SqListType.h"
void InitList(SqList &L);
void DestroyList(SqList &L);
void ClearList(SqList &L);
Status ListEmpty(SqList L);
int ListLength(SqList L);
Status GetElem(SqList L,int pos,ElemType &e);
int LocateElem(SqList L,ElemType e,Status(*compare)(ElemType,ElemType));
Status PriorElem(SqList L,ElemType cur_e,ElemType &pre_e);
Status NextElem(SqList L,ElemType cur_e,ElemType &next_e);
Status ListInsert(SqList &L,int pos,ElemType e);
Status ListDelete(SqList &L,int pos,ElemType &e);
void ListTraverse(SqList L,void(*vi)(ElemType&));
#endif

SqListTestMain.cpp

// SqListTestMain.cpp 检验SqListBasicOperation.cpp的主程序
#include"c1.h"
#include"SqListType.h"
#include"Compare.h" // 包括equal()、comp()、Dprint()、Cprint()和CitePrint()函数
#include"SqListBasicOperation.h"
// 数据元素判定函数 (平方关系 ) , LocateElem() 调用的函数
Status sq(ElemType c1, ElemType c2);


// ListTraverse() 调用的另一函数 (元素值加倍 )
void ElemDouble(ElemType &Citec);
void main()
{
	SqList L;
	ElemType e,e0;
	Status i;
	int j,k;
	InitList(L);
	printf("初始化L后:L.elem=%u L.length=%d L.listsize=%d\n",L.elem,L.length,L.listsize);
	for(j=1;j<=5;j++)
		i=ListInsert(L,1,j);
	printf("在L的表头依次插入1~5后:*L.elem=");
	for(j=1;j<=5;j++)
		cout<<*(L.elem+j-1)<<' ';
	cout<<endl;
	printf("L.elem=%u L.length=%d L.listsize=%d ",L.elem,L.length,L.listsize);
	i=ListEmpty(L);
	printf("L是否空:i=%d(1:是 0:否)\n",i);
	ClearList(L);
	printf("清空L后:L.elem=%u L.length=%d L.listsize=%d ",L.elem,L.length,L.listsize);
	i=ListEmpty(L);
	printf("L是否空:i=%d(1:是 0:否)\n",i);
	for(j=1;j<=10;j++)
		ListInsert(L,j,j);
	printf("在L的表尾依次插入1~10后:*L.elem=");
	for(j=1;j<=10;j++)
		cout<<*(L.elem+j-1)<<' ';
	cout<<endl;
	printf("L.elem=%u L.length=%d L.listsize=%d\n",L.elem,L.length,L.listsize);
	ListInsert(L,1,0);
	printf("在L的表头插入0后:*L.elem=");
	for(j=1;j<=ListLength(L);j++) // ListLength(L)为元素个数
		cout<<*(L.elem+j-1)<<' ';
	cout<<endl;
	printf("L.elem=%u(有可能改变) L.length=%d(改变) L.listsize=%d(改变)\n",L.elem,L.length,L.listsize);
	GetElem(L,5,e);
	printf("第5个元素的值为:%d\n",e);
	for(j=10;j<=11;j++)
	{
		k=LocateElem(L,j,equal);
		if(k) // k不为0,表明有符合条件的元素,且其位序为k
			printf("第%d个元素的值为%d\n",k,j);
		else
			printf("没有值为%d的元素\n",j);
	}
	for(j=3;j<=4;j++)
	{
		k=LocateElem(L,j,sq);
		if(k) // k不为0,表明有符合条件的元素,且其位序为k
			printf("第%d个元素的值为%d的平方\n",k,j);
		else
			printf("没有值为%d的平方的元素\n",j);
	}
	for(j=1;j<=2;j++) // 测试头两个数据
	{
		GetElem(L,j,e0); // 把第j个数据赋给e0
		i=PriorElem(L,e0,e); // 求e0的前驱
		if(i==INFEASIBLE)
			printf("元素%d无前驱\n",e0);
		else
			printf("元素%d的前驱为:%d\n",e0,e);
	}
	for(j=ListLength(L)-1;j<=ListLength(L);j++) // 最后两个数据
	{
		GetElem(L,j,e0); // 把第j个数据赋给e0
		i=NextElem(L,e0,e); // 求e0的后继
		if(i==INFEASIBLE)
			printf("元素%d无后继\n",e0);
		else
			printf("元素%d的后继为:%d\n",e0,e);
	}
	k=ListLength(L); // k为表长
	for(j=k+1;j>=k;j--)
	{
		i=ListDelete(L,j,e); // 删除第j个数据
		if(i==ERROR)
			printf("删除第%d个元素失败\n",j);
		else
			printf("删除第%d个元素成功,其值为:%d\n",j,e);
	}
	printf("依次输出L的元素:");
	ListTraverse(L,CitePrint); // 依次对元素调用CitePrint(),输出元素的值
	printf("L的元素值加倍后:");
	ListTraverse(L,ElemDouble); // 依次对元素调用ElemDouble(),元素值乘2
	ListTraverse(L,CitePrint);
	DestroyList(L);
	printf("销毁L后:L.elem=%u L.length=%d L.listsize=%d\n",L.elem,L.length,L.listsize);
	getchar();
}
Status sq(ElemType c1,ElemType c2)
{ // 数据元素判定函数(平方关系),LocateElem()调用的函数
	if(c1==c2*c2)
		return TRUE;
	else
		return FALSE;
}

void ElemDouble(ElemType &c)
{ // ListTraverse()调用的另一函数(元素值加倍)
	c*=2;
}

SqListType.h

#pragma once
#ifndef _SQLISTTYPE_H_
#define _SQLISTTYPE_H_

#define LIST_INIT_SIZE 10/*1*/
#define LIST_INCREMENT 2/*2*/
typedef int ElemType;
struct SqList{
	ElemType *elem;/*3*/
	int length;/*4*/
	int listsize;/*5*/
};
#endif

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值