循环链表
有尾指针很容易找到头指针,但是有头指针不是很方便找尾指针。
所以循环单链表一般习惯带尾指针。(表头指针指向尾部)
list
指向的节点data域
不存值
typedef struct node{
int data;
struct node *next;
}nod,*Node;
// 单向递增的循环链表中插入 insData ,list 是表头指针, 指向链条尾部
void insert_order(Node list,int insData){
Node pNew=(Node)malloc(sizeof(nod));
pNew->data=insData;
// 如果 是空链表 或者 insData 很小
if(list->next==list||list->next->data>=insData){
pNew->next=list->next;
list->next=pNew;
}else if(list->next->data<insData){
Node pre=list->next;
while(pre->next->data<insData&&pre->next!=list){
pre=pre->next;
}
// 在 pre 之后 插入
pNew->next=pre->next;
pre->next=pNew;
}
}
int deleteData(struct node *list, int delData)
{
//删除所有值为 delData的结点, 返回值为删除结点的个数
int count=0;
Node p=list;
while(p->next!=list){
// p 是待删节点的前驱
if(p->next->data==delData){
Node q=p->next;
p->next=q->next;
free(q);
count++;
// 进行删除后 无需移位, p->next 已更新了
}else{
p=p->next;
}
}
return count;
}
一定要注意,这样的事,改变L是无效的,函数出来之后 L还是原来的指向。
想要改变,就用引用 int *& L。
void(int *L){
int *p;
L=p; // 无效
}
双向链表
在单链表中,查找前驱节点不方便。
typedef struct node{
int data;
struct node *prior,*next;
}nod,*Node;
创建
Node list=(Node)malloc(sizeof(nod));
list->prior=NULL;
list->next=NULL;
void insertDlist(struct node *list, int insData){
//在双向链表的表头插入数据, list 指向头部,不存值。
Node pNew=(Node)malloc(sizeof(nod));
pNew->data=insData;
// 如果是空的 ,建两条链就可以 不是空的, 建4条链
if(list->prior==NULL&&list->next==NULL){
list->next=pNew;
pNew->prior=list;
pNew->next=NULL;
}else{
list->next->prior=pNew;
pNew->next=list->next;
list->next=pNew;
pNew->prior=list;
}
}
尾插
// r 是尾指针
r->next=pNew; // 建立后继关系
pNew->prior=r; // 建立前驱关系
r=pNew; // 更新 r
删除
删除P指向的节点。
p->prior->next=p->next;
p->next->prior=p->prior;
free(p);
静态链表
有些语言并没有提供指针这种数据类型,想要使用链表结构,可以采用数组来模拟实现链表。
在这个数组里,物理上相邻的数据元素逻辑上并不一定相邻。
定义一个较大的数组作为节点空间的存储池。
# define Maxsize 10
typedef int Datatype;
typedef struct SNode{
Datatype data;
int next;
}Snode,StaticList[Maxsize+1];
// Staticlist代表的是 struct SNode [11] 类型, 数组中每个元素都是一个 struct SNode
StaticList L;
L[8].next=6 // 说明 后驱为 L[6]
静态链表中,还需要有一条连接各个空闲位置的链表,称为备用链表。
查找
// 以 body 为头节点的链表,查找 数值域为 elem 的节点在数组中的位置
int find_data(StaticList L,int body,char elem){
while(L[body].next){
if(L[body].data==elem){
return body;
}
body=L[body].next;
}
return -1; // 表示没找到
}
参考来源
静态链表