线性表
2013-05-25 21:26
330 查看
线性表:顺序表和链表六种基本操作:
InitList(&L) //构造一个空的线性表LListLength(L) //获取线性表L的元素个数
GetNode(L, i) //获取线性表L第i个元素
LocateNode(L, e) //查找线性表值为e的元素的位置
ListInsert(L, i, &e) //在线性表L的第i个位置插入元素e
DeleteNode(L, i) //删除线性表L的第i个元素
一、顺序表
#define OK 1 #define ERROR -1 #define MAX_SIZE 100 //MAX_SIZE大小需根据具体情况而定,这里假设是100 #typedef int Status; #typedef int ElemType; typedef struct sqlist{ ElemType Elem_array[MAX_SIZE]; int length; }SqList;
1.1 初始化
Status Init_SqList(SqList *L) { L->Elem_array = (ElemType *)malloc(MAX_SIZE*sizeof(ElemType)); if(!L->Elem_array) return ERROR; else { L->length = 0; return OK; } }
1.2 查找
int Locate_SqList(SqList *L, ElemType x) { int i=0; while(i<L->length) if(L_Elem_array[i] != x) i++; else return ++i; //要查找的值在线性表L第++i个位置 if(i>L->length) { printf(“要删除的数据元素不存在!\n”); return ERROR; } }
1.3 插入
Status Insert_SqList(SqList *L, int i, ElemType e) //在顺序表L中第i个位置插入元素e { int j; if(i<0||i>L->length-1) return ERROR; if(L->length>=MAX_SIZE) { printf("线性表溢出!\n"); return ERROR; } for(j=L->length-1; j>=i-1; --j) L->Elem_array[j+1] = L->Elem_array[j]; //i-1位置以后的所以结点后移 L->Elem_array[i-1] = e; //在i-1位置插入结点e L->length++; return OK; }
1.4 删除
ElemType Delete_SqList(SqList *L, int i) { int k; ElemType x; if(L->length == 0) { printf("线性表L为空!\n"); return ERROR; } else if(i<1||i>L->length) { printf("要删除的数据元素不存在!\n"); return ERROR; } else { x = L->Elem_array[i-1]; //保存结点的值 for(k=i; k<L->length; k++) L->Elem_array[k-1] = L->Elem_array[k]; //i位置以后的所有结点前移 L->length--; return x; } }
二、单链表
typedef struct Lnode{ ElemType data; //数据域,保存结点的值 struct Lnode *next; //指针域 }LNode; //结点类型
2.1 头插入法建表
/*头插入法创建单链表,链表的头结点head作为返回值*/ LNode *create_LinkList(void) { int data; LNode *head, *p; head = (LNode *)malloc(sizeof(LNode)); head->next = NULL; //创建单链表头结点head while(1) { scanf("%d", &data); //data值和类型可以根据具体情况得到 if(data == 32767) //32767定义为判断创建链表结束条件 break; p = (LNode *)malloc(sizeof(LNode)); p->data = data; //数据域赋值 p->next = head->next; head->next = p; //钩链,新创建的结点总是作为第一个结点 } return head; }
2.2 尾插入法建表
/*尾插入法创建单链表,链表的头结点head作为返回值*/ LNode *create_LinkList(void) { int data; LNode *head, *p, *q; head = p = (LNode *)malloc(sizeof(LNode)); p->next = NULL; //创建单链表头结点head while(1) { scanf("%d", &data); //data值和类型可以根据具体情况得到 if(data == 32767) //32767定义为判断创建链表结束条件 break; q = (LNode *)malloc(sizeof(LNode)); q->data = data; //数据域赋值 q->next = p->next; p->next = q; p = q; //钩链,新创建的结点总是作为第一个结点 } return head; }
2.3 按序号查找
Elem_Type Get_Node(LNode *L, int i) //在单链表L中查找第i个结点 { int j; LNode *p; p = L->next; j = 1; //使p指向第一个结点 while(p!=NULL && j<i) //p为NULL表示i太大;j>i表示i为0; { p = p->next; j++; //移动指针p,j计数 } if(j!=i) return -32768; else return p->data; }
2.4 按值查找
LNode *Locate_Node(LNode *L, int key) //在单链表L中查找值为key的结点 { LNode *p = L->next; while(p!=NULL && p->data != key) p = p->next; if(p->data == key) return p; else { printf("所要查找的结点不存在!\n"); return NULL; } }
2.5 插入
/*在以L为头结点的单链表的第i个位置插入值为e的结点*/ void Insert_LNode(LNode *L, int i, ElemType e) { int j = 0; LNode *p, *q; p = L->next; while(p!=NULL && j<i-1) { p = p->next; j++; } if(j!=i-1) printf("i太大或i为0!\n"); else { q = (LNode *)malloc(sizeof(LNode)); q->data = e; q->next = p->next; p->next = q; } }
2.6 按序号删除
/*删除以L为头结点的单链表中的第i个结点*/ void Delete_LinkList(LNode *L, int i) { int j=1; LNode *p = L, *q = L->next; while(p->next!=NULL && j<i) { p = q; q = q->next; j++; } if(j!=i) printf("i太大或i为0!\n"); else { p->next = q->next; free(q); } }
2.7 按值删除
/*删除以L为头结点的单链表中值为key的第一个结点*/ void Delete_LinkList(LNode *L, int key) { LNode *p = L, *q = L->next; while(q!=NULL && q->data!=key) { p = q; q = q->next; } if(q->data == key) { p->next = q->next; free(q); } else printf("所要删除的结点不存在!\n"); }
/*按值删除值为key的所有结点*/ void Delete_LinkList_Node(LNode *L, int key) { LNode *p = L, *q = L->next; while(q!=NULL) { if(q->data==key) { p->next = q->next; free(q); q = p->next; } else { p = q; q = q->next; } } }
/*删除以L为头结点的单链表中所有值相同的结点*/ void Delete_Node_value(LNode *L) { LNode *p = L->next, *q, *ptr; while(p!=NULL) //检查链表中所有结点 { q = p; ptr = p->next; while(ptr != NULL) //检查结点p的所有后继结点ptr { if(ptr->data == p->data) { q->next = ptr->next; free(ptr); ptr = q->next; } else { q = ptr; ptr = ptr->next; } } p = p->next; } }
2.8 合并
/*合并以La,Lb为头结点的两个有序单链表*/ LNode *Merge_LinkList(LNode *La, LNode *Lb) { LNode *Lc, *pa, *pb, *pc, *ptr; Lc = La; pc = La; pa = La->next; pb = Lb->next; while(pa!=NULL &&pb!=NULL) { //将pa所指的结点合并,pa指向下一个结点 if(pa->data < pb->data) { pc->next = pa; pc = pa; pa = pa->next; } //将pb所指的结点合并,pb指向下一个结点 if(pa->data > pb->data) { pc->next = pb; pc = pb; pb = pb->next; } //将pa所指的结点合并,pb所指的结点删除 if(pa->data == pb->data) { pc->next = pa; pc = pa; pa = pa->next; ptr = pb; pb = pb->next; free(ptr); } } if(pa != NULL) pc->next = pa; else pc->next = pb; //将剩余的结点链上 free(Lb); return Lc; }
三、循环链表
判断是否空链表: head->next == head;判断是否表尾结点: p->next == head;
四、双向链表
typedef struct Dulnode{ ElemType data; struct Dulnode *prior, *next; }DulNode;
4.1 插入
插入时仅仅指出直接前驱结点,钩链时必须注意先后次序是:“先右后左”。部分语句组如下:S = (DulNode *)malloc(sizeof(DulNode)); S->data = e; S->next = p->next; p->next->prior = S; p->next = S; S->prior = p;
插入时同时指出直接前驱结点p和直接后继结点q,钩链时无须注意先后次序。部分语句组如下:
S = (DulNode *)malloc(sizeof(DulNode)); S->data = e; p->next = S; S->next = q; S->prior = p; q->prior = S;
4.2 删除
设要删除的结点为p,删除时可以不引人新的辅助指针变量,可以直接先断链,再释放结点。部分语句组如下:p->prior->next = p->next; p->next->prior = p->prior; free(p);
相关文章推荐
- 线性表(一)
- 比较总结线性表的几种主要存储结果
- 线性表综合实验之双链表的实现
- 软考复习:数据结构基础(1.1线性表)
- C++中将数组线性表转换为链表
- C++中将链表转换为数组描述的线性表
- C/C++ 第四周线性表(二)--链表 项目一 建立单链表
- 线性表
- C/C++ 第五周线性表 项目(一)建立顺序栈的算法库
- 数据结构 - 线性表
- 基于C语言数据结构-线性表
- C/C++ 第五周线性表 项目(二)建立链栈算法库
- 已知A,B,C为三个元素值递增有序的线性表,要求对表A如下运算:删去那些既在表B中出现又在表C
- 数据结构(一)顺序表和线性表重点概述
- 算法系列15天速成——第八天 线性表【下】
- 学习总结-线性表一
- 线性表
- 线性表 - 顺序存储结构
- 数据结构学习笔记——线性表(上)
- 数据结构详解——线性表(C++实现)