您的位置:首页 > 编程语言 > C语言/C++

C语言实现单链表

2011-09-04 02:07 387 查看
/*
* link_list.h
*
*  Created on: 2011-9-2
*      Author: liusheng
*/

#ifndef LINK_LIST_H_
#define LINK_LIST_H_

#define ElemType int
#define FALSE 0;
#define TRUE 1;
typedef struct list_node {
ElemType date;
struct list_node *next;
}node,*linklist;

//初始化单链表
int initlinklist(linklist *l) {
(*l) = (node *)malloc(sizeof(node));
if(*l == NULL) return FALSE;
(*l)->next = NULL;
(*l)->date = 0;
return TRUE;
}
/*linklist initlinklist() {
node *l = NULL;
l = (node *)malloc(sizeof(node));
if(l == NULL) return l;
l->date = 0;//将链表的长度设为0
l->next = NULL;
printf("%d\n",l);
return l;
}*/
//用头插发建立单链表
int addnodehead(linklist l,ElemType e) {
node *s;
s = (node *)malloc(sizeof(node));
if(s == NULL) return FALSE;
s->next = l->next;
l->next = s;
s->date = e;
l->date ++;
return TRUE;
}
//用尾插法建立单链表
int addnodetail(linklist l,ElemType e) {
node *s,*addnode;
s = l;
while(s->next != NULL) {
s = s->next;
}
addnode = (node *)malloc(sizeof(node));
if(addnode == NULL) return FALSE;
s->next = addnode;//将新的节点的地址给s
addnode->date = e;
addnode->next = NULL;
l->date ++;
return TRUE;
}
//在链表的第i个数据前插入数据
int insertlinklistnode(linklist l,int i,ElemType e) {
if(i<1 || i>l->date) return FALSE;
node *s,*addnode;
s = l;
while(i > 1) {
s = s->next;
i --;
}
addnode = (node *)malloc(sizeof(node));
addnode->next = s->next;
s->next = addnode;
addnode->date = e;
l->date ++;
return TRUE;
}
//删除链表指定的第i个数据
int deletelinklistnode(linklist l,int i,ElemType *e) {
if(i<1 || i>l->date) return FALSE;
node *s;
s = l;
while(i > 1) {
s = s->next;
i --;
}
node *temp;
temp = s->next;
(*e) = temp->date;
s->next = s->next->next;
free(temp);
l->date --;
return TRUE
}
//删除单链表中指定了值的数据
int deleteelem(linklist l,ElemType e) {
node *s;
s = l;
int count = 0;//记录一空删除了几个值
int temp = 0;//遍历元素的个数
while(s->next != NULL) {
s = s->next;
temp ++;
if(s->date == e) {
count ++;
deletelinklistnode(l,temp,&e);
temp --;
}
}
return count;
}
//若Elemtype为int将链表中的数据从小到大排序
void sortlinklist(linklist l) {
node *first,*final;
final = l;
while(final->next != NULL) {
final = final->next;
}
first = l->next;
int temp = 0;
while(final != l->next) {
while(first != final) {
if(first->date > first->next->date) {
temp = first->date;
first->date = first->next->date;
first->next->date = temp;
}
temp = (int)first;//记录final前一个节点的地址
first = first->next;
}
first = l->next;
final = (node *)temp;
}
}
/*
* 将两张有序单链表合并一张有序单链表,不用前面的sortlinklist方法
* 当然单张的有序单链表要使用sortlinklist排序
*/

linklist combinelinklist(linklist la,linklist lb) {
linklist lc;
node *pa,*pb,*pc;
lc = la;
pa = la->next;
pb = lb->next;
pc = lc;
while(pa != NULL && pb != NULL) {
if(pa->date < pb->date) {
pc->next = pa;//这段代码是关键
pc = pa;
pa = pa->next;
} else {
pc->next = pb;
pc = pb;
pb = pb->next;
}
}
pc->next = pa?pa:pb;
return lc;
}

//输出单链表中的所有元素
void printfnode(linklist l) {
node *s;
s = l->next;//存储第一个节点的地址
while(s!= NULL) {
printf(" date = %d",s->date);
s = s->next;//与上面一行有什么区别
}
}
#endif /* LINK_LIST_H_ */

/*
* linklist.c
* 对link_list.h测试
*  Created on: 2011-9-2
*      Author: liusheng
*/
#include <stdio.h>
#include <stdlib.h>
#include "link_list.h"
int main(void) {
linklist l = NULL;//第一个节点
//l = initlinklist();//将链表初始化l->next = NULL;
initlinklist(&l);
addnodehead(l,10);
addnodehead(l,20);
addnodehead(l,30);
addnodehead(l,40);
addnodetail(l,5);
addnodetail(l,6);
addnodetail(l,6);
printfnode(l);
printf("\n");
printf("%d\n",l->date);
//测试插入节点
insertlinklistnode(l,2,8);
printfnode(l);
printf("\n");
printf("%d\n",l->date);

//测试删除指定节点
ElemType e;
deletelinklistnode(l,3,&e);
deletelinklistnode(l,3,&e);
deletelinklistnode(l,3,&e);
printfnode(l);
printf("\n");
printf("%d\n",l->date);
printf("%d\n",e);
deleteelem(l,6);
printfnode(l);
printf("\n");
printf("%d\n",l->date);
//测试将链表排序
sortlinklist(l);
printfnode(l);
printf("\n");
printf("%d\n",l->date);

//测试将两个顺序链表合并成一个链表
linklist lb,lc;
initlinklist(&lb);
initlinklist(&lc);
addnodehead(lb,100);
addnodehead(lb,8);
addnodehead(lb,16);
addnodehead(lb,4);
addnodehead(lb,99);
sortlinklist(lb);
printfnode(lb);
printf("\n");
lc = combinelinklist(l,lb);
printfnode(lc);
return 0;
}

以下是测试后的结果

date = 40 date = 30 date = 20 date = 10 date = 5 date = 6 date = 6
7
date = 40 date = 8 date = 30 date = 20 date = 10 date = 5 date = 6 date = 6
8
date = 40 date = 8 date = 5 date = 6 date = 6
5
10
date = 40 date = 8 date = 5
3
date = 5 date = 8 date = 40
3
date = 4 date = 8 date = 16 date = 99 date = 100
date = 4 date = 5 date = 8 date = 8 date = 16 date = 40 date = 99 date = 100
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: