线性表的链式表示和实现(单链表)

本文是对严蔚敏老师《数据结构》线性表的链式表示和实现这节的算法用C语言的实现,已成功在Linux上运行。

#include <stdlib.h>
#include <malloc.h>

//函数结果代码
#define TRUE       1
#define FALSE      0
#define OK         0
#define ERROR      1
#define OVERFLOW  -1

typedef int Status;           //函数的类型,其结果是函数结果状态代码

//线性表的单链表存储结构
typedef struct LNode{
	int data;              //数据域
	struct LNode * next;   //指针域
}LNode, * LinkList;

//函数声明
void CreateList_L(LinkList *, int);
Status TraverseList_L(LinkList);
Status GetElem(LinkList,int,int *);
Status ListInsert_L(LinkList *, int, int);
Status ListDelete_L(LinkList *, int, int *);
void MergerList_L(LinkList, LinkList, LinkList *);

Status main(void) 
{	
	//int e;
	LinkList La, Lb, Lc;      //头指针
	CreateList_L(&La, 4);
	TraverseList_L(La);

	CreateList_L(&Lb, 7);
	TraverseList_L(Lb);
	MergerList_L(La,Lb,&Lc);	
	TraverseList_L(Lc);

	//ListInsert_L(&L,3,100);

	//TraverseList_L(L);

	//ListDelete_L(&L,3,&e);
	//printf("%d\n",e);
	//TraverseList_L(L);

	//GetElem(L,3,&e);
	//printf("%d\n",e);

	return OK;
}


//创建链表,逆位序输入n个元素的值,建立带表头结点的单链表线性表L
void CreateList_L(LinkList * L, int n)
{
	int i;
	LinkList p;
	*L = (LinkList)malloc(sizeof(LNode));  //头结点
	(*L)->next = NULL;      //先创建一个带有头结点的空链表

	for (i=n; i>0; --i) {
		p = (LinkList)malloc(sizeof(LNode));   //生成新结点
		printf("请输入第%d个结点的值:",i);
		scanf("%d",&p->data);
		p->next = (*L)->next;    //插入到表头
		(*L)->next = p;
	}
}

//遍历输出
Status TraverseList_L(LinkList L)
{
	LinkList p = L->next;

	if (NULL == p) {       //判断线性表是否为空
		printf("线性表为空!\n");
		return ERROR;	
	}
	while (p) {
		printf("%d\t",p->data);
		p = p->next;
	}
	printf("\n");
	
	return OK;
}

//用e返回L中第i个数据元素的值. 若第i个元素不存在则返回ERROR
Status GetElem(LinkList L,int i,int * e)
{
	int j = 1;      //j为计数器
	LinkList p = L->next;  //p指向第一个结点

	while (p && (j<i)) {   //顺指针向后查找,直到p指向第i个元素或p为空
		p = p->next;
		++j;
	}
	
	if (!p || (j>i))         //!p保证i在链表的长度之内,j>i保证i不比1小
		return ERROR;         //第i个元素不存在
	*e = p->data;            //取出第i个元素的值
	return OK;
}

//在带头结点的单链表L中的第i个位置之前插入新的数据元素e
Status ListInsert_L(LinkList * L, int i, int e)
{	
	int j = 1;      //j为计数器
	LinkList p,s;
	p = *L;  //p指向头结点

	while (p && (j<i)) {   //顺指针向后查找,直到p指向第i个元素或p为空
		p = p->next;
		++j;
	}
	if (!p || (j>i))         //!p保证i在链表的长度之内,j>i保证i不比1小
		return ERROR;         //第i个元素不存在
	
	s = (LinkList)malloc(sizeof(LNode));   //生成新结点
	s->data = e;

	s->next = p->next;
	p->next = s;
	
	return OK;
}

//在带头结点的单链表L中,删除第i个结点,并由e返回其值
Status ListDelete_L(LinkList * L, int i, int * e)
{	
	int j = 1;      //j为计数器
	LinkList p,q;
	p = *L;  //p指向头结点

	while (p && (j<i)) {   //顺指针向后查找,直到p指向第i个元素或p为空
		p = p->next;
		++j;
	}
	if (!p || (j>i))         //!p保证i在链表的长度之内,j>i保证i不比1小
		return ERROR;         //第i个元素不存在

	q = p->next;
	p->next = q->next;    //删除结点
	*e = q->data;
	free(q);        //释放结点
	
	return OK;
}

//已知单链表表La和Lb中的数据元素按值非递减排序,归并La和Lc得到新的单链表Lc,Lc的数据元素也按值非递减排序
void MergerList_L(LinkList La, LinkList Lb, LinkList * Lc)
{
	LinkList pa, pb, pc;

	pa = La->next;
	pb = Lb->next;
	*Lc = pc = La;   //用La的头结点作为Lc的头结点

	while (pa && pb ) {   //La和Lb均非空

		if ( pa->data <= pb->data) {
			pc->next = pa;
			pc = pa;
			pa = pa->next;
		}else {
			pc->next = pb;
			pc = pb;
			pb = pb->next;

		}
	}
	pc->next = pa?pa:pb;
	free(Lb);
	
	return;
}


  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值