软件编程
位置:首页>> 软件编程>> C语言>> C语言实现双向链表

C语言实现双向链表

作者:hebedich  发布时间:2023-05-30 08:02:24 

标签:C语言,双向链表

这个小代码是我凭自己对指针和链表的理解和认识,自己实现的,没有参考其他人的代码,如果有相同的地方,那真的只是巧合,代码我在ubuntu 15.04下测试通过,可能存在很多错误和漏洞.

doublelist.c


/*************************************************************************
 > File Name: doublelist.c
 > Author: ChenYiLiang
 > Mail: chenyiliangex@163.com
 > Created Time: Sat 21 Mar 2015 07:32:22 PM CST
************************************************************************/

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

struct userdata{
 int userid;
 char username[30];

struct userdata *previous;
 struct userdata *next;
};

struct userdata *header;
size_t scanf_id;
char scanf_name[30];

int yesno;
int deletePosition;
int alterPosition;
int alterId;
char alterName[30];

int searchPosition;

FILE *ptr_fpid;

/*向链表中插入数据*/
int insert_list(struct userdata *header, size_t position, char name[], size_t id);
/*删除链表中指定的节点*/
int delete_node(struct userdata *header, size_t position);
/*修改指定位置的节点信息*/
int alter_node(struct userdata *header, size_t position, size_t id, char name[]);
/*查找链表中的数据*/
struct userdata *search_node(struct userdata *header, size_t position);
/*遍历链表*/
int travel_list(struct userdata *header);
/*判断链表是空*/
int isempty(struct userdata *header);

/*将链表结构写入文件*/
int write_into_file(struct userdata *header, FILE *fp);
/*从文件读取数据放到链表中*/
int read_from_file(struct userdata *header, FILE *fp);

int main(){
 struct userdata *header_node = (struct userdata *)malloc(sizeof(struct userdata));
 header_node -> previous = NULL;
 header_node -> next = NULL;

read_from_file(header_node, ptr_fpid);
 travel_list(header_node);
 while(1){
 //scanf("%*[^\n]");
 //scanf("%*c");
 //scanf("%*[^\n]");
 printf("please input id - ");
 scanf("%d", &scanf_id);
 //scanf("%*c");
 //scanf("%*[^\n]");
 printf("please input your name - ");
 scanf("%s", scanf_name);

printf("%d - %s\n\n", scanf_id, scanf_name);

//isempty(header_node);

/*0表示默认插入到链表的尾部*/
 insert_list(header_node, 0, scanf_name, scanf_id);

//write_into_file(header_node, ptr_fpid);
 //isempty(header_node);

printf("input anymore - ");
   scanf("%d", &yesno);
   if(yesno == -1){
     break;
   }

scanf("%*c");
 scanf("%*[^\n]");
// travel_list(header_node);

}
 getchar();
 //printf("delete position data - ");
 //scanf("%d", &deletePosition);
 //delete_node(header_node, deletePosition);

// printf("alter data for position - ");
// scanf("%d", &alterPosition);
// printf("please inout new id - ");
// scanf("%d",&alterId);
// printf("please input new name - ");
// scanf("%s", alterName);
// alter_node(header_node, alterPosition, alterId, alterName);
 write_into_file(header_node, ptr_fpid);
 travel_list(header_node);
 printf("\n\n");
 printf("please input position to search - ");
 scanf("%d", &searchPosition);
 struct userdata *searchData = search_node(header_node, searchPosition);
 printf("%d\n", searchData -> userid);
 printf("%s\n", searchData -> username);
 return 0;
}

/* 插入节点 */
int insert_list(struct userdata *header, size_t position, char name[], size_t id ){
 struct userdata *temp_newuser = header;
 struct userdata *getMemory = (struct userdata *)malloc(sizeof(struct userdata));

getMemory -> userid = id;
 strncpy(getMemory -> username, name, 30);
 /*当position == 0时,表示默认插入到链表的尾部*/
 if(0 == position){
   if(NULL != temp_newuser -> next){
     while(NULL != temp_newuser -> next){
       temp_newuser = temp_newuser -> next;
     }
   }
 }

/*当position > 1时则寻找合适的位置插入*/
 if(1 <= position){
   for(int i = 0; i <= position; i++){
     /*当执行此处的代码时表示,链表已经到达尾部或者是空链表*/
     if(NULL == temp_newuser -> next){
       break;
     }
     temp_newuser = temp_newuser -> next;
   }
 }

getMemory -> previous = temp_newuser;
 if(temp_newuser -> next == NULL){
   temp_newuser -> next = getMemory;
   getMemory -> next = NULL;
 }else{
   temp_newuser -> next -> previous = getMemory;
   getMemory -> next = temp_newuser -> next;
   temp_newuser -> next = getMemory;
 }

return 0;
}

/*删除链表中指定的节点*/
int delete_node(struct userdata *header, size_t position){
 int is_empty = isempty(header);
 if(0 == is_empty){
   printf("this si a empty list!\n\n");
   return -1;
 }

struct userdata *deleteNode = header;

for(int i = 0; i < position; i++ ){
     /*当执行此处的代码时表示,链表已经到达尾部或者是空链表*/
     if(NULL == deleteNode -> next){
       break;
     }
     deleteNode = deleteNode -> next;
   }

/**/
 deleteNode -> next -> previous = deleteNode -> previous;
 deleteNode -> previous -> next = deleteNode -> next;
 free(deleteNode);

return 0;  
}

/*修改指定位置的节点信息*/
int alter_node(struct userdata *header, size_t position, size_t id, char name[]){
 int isEmpty = isempty(header);
 if(0 == isEmpty){
   printf("this is a empty list\n\n");
   return -1;
 }

struct userdata *alterNode = header;
   for(int i = 0; i < position; i++ ){
     /*当执行此处的代码时表示,链表已经到达尾部或者是空链表*/
     if(NULL == alterNode -> next){
       break;
     }
     alterNode = alterNode -> next;
   }

alterNode -> userid = id;
   strncpy(alterNode -> username, name, 30);

return 0;
}

/*查找链表中的数据*/
struct userdata *search_node(struct userdata *header, size_t position){
 int isEmpty = isempty(header);
 if(0 == isEmpty){
   printf("this is a empty!\n");
   return NULL;
 }

struct userdata *searchNode = header;
 for(int i = 0; i < position; i++){
   if(NULL == searchNode -> next){
     break;
   }
   searchNode = searchNode -> next;
 }

return searchNode;
}

/*遍历链表*/
int travel_list(struct userdata *header){
 struct userdata *travel = header;
 if(NULL == travel -> next){
   printf("This is a empty list!!\n");
   return 1;
 }

for(travel = travel -> next ; ; travel = travel -> next){
   printf("%d\n",travel -> userid);
   printf("%s\n", travel -> username);
   if(NULL == travel -> next){
     break;
   }
 }  

return 1;
}

/*判断链表是空*/
int isempty(struct userdata *header){
 if(header -> next == NULL){
   return 0;
 }else{
   return 1;
 }
}

/*将链表结构写入文件*/
int write_into_file(struct userdata *header, FILE *fp){
 fp = fopen("listdata", "wb");
 if(NULL == fp){
   perror("open file failed when write into file!"),exit(-1);
 }

printf("come into write!\n");
 for(struct userdata *move = header -> next; ; move = move -> next){
   fwrite(move,sizeof(struct userdata), 1, fp);
   if(NULL == move -> next){
     break;
   }
 }
 fclose(fp);
 fp = NULL;
 return 0;
}
/*从文件读取数据放到链表中*/
int read_from_file(struct userdata *header, FILE *fp){
 struct userdata *readfile = header;
 fp = fopen("listdata", "rb");
 if(NULL == fp){
   perror("open file failed when read - ");
   return -1;
 }

while(1){
   struct userdata *newread = (struct userdata *)malloc(sizeof(struct userdata));
   fread(newread, sizeof(struct userdata), 1, fp);
   if(feof(fp)){/*当读取到文件的尾部时.跳出循环*/
     break;
   }
   readfile -> next = newread;
   newread -> next = NULL;
   newread -> previous = readfile;
   readfile = newread;
 }
 fclose(fp);
 fp = NULL;
 return 0;
}

C语言实现双向链表

C语言实现双向链表

C语言实现双向链表删除节点、插入节点、双向输出等操作


#include<cstdio>  
#include<cstdlib>  
typedef struct DoubleLinkedList
{
 int data;
 struct DoubleLinkedList *pre;
 struct DoubleLinkedList *next;
}DlinkedList_Node;
//建立链表  
DlinkedList_Node* createDLink()
{
 DlinkedList_Node *head,*p,*s;
 int x;
 head = (DlinkedList_Node*)malloc(sizeof(DlinkedList_Node));
 p = head;
 while(1)
 {
   printf("please input the data: \n");
   scanf("%d",&x);
   if(x != 65535)
   {
     s = (DlinkedList_Node*)malloc(sizeof(DlinkedList_Node));
     s ->data = x;
     s-> pre = p;
     p->next = s;
     p=s;
   }
   else
     {
       printf("\n数据输入结束\n");
       break;
     }
 }
 p->next = NULL;
 head = head ->next;
 head->pre = NULL;
 return head;
}
//顺序、反序打印链表  
void printDLink(DlinkedList_Node *head)
{
 DlinkedList_Node *p,*s;
 p = head;
 printf("正序输出双向链表:\n");
 while(p)
 {
   printf("%d ",p->data);
   s = p;
   p = p->next;
 }
 printf("\n 逆序输出双向链表: \n");
 while(s)
 {
   printf("%d ",s->data);
   s = s->pre;
 }
 printf("\n \n");
}
//删除一个结点  
DlinkedList_Node* deleteDlinkedList_Node(DlinkedList_Node *head,int i)
{
 DlinkedList_Node *p;
 p = head;
 if(p->data == i)
 {
   head = p->next;
   head->pre = NULL;
   free(p);
   return head;
 }
 while(p)
 {
   if(p->data == i)
   {
   p->pre->next = p->next;
   p->next->pre = p->pre;
   free(p);
   return head;
   }
   p = p->next;
 }
 printf("没有找到想要删除的数据\n");
 return head;
}
//插入一个结点  
DlinkedList_Node* insertDlinkedList_Node(DlinkedList_Node *head,int i)
{
 DlinkedList_Node *p,*temp;
 p = head;
 temp = (DlinkedList_Node*)malloc(sizeof(DlinkedList_Node));
 temp ->data = i;
 if(i < p->data)//比头结点数据小,插入到链表头部  
 {
   head = temp;
   head->next = p;//此处p为原来的head  
   head->pre = NULL;
   p->pre = head;//此处p为原来的head  
   return head;
 }
 while(p != NULL && i > p->data)//寻找合适的插入位置  
 {
   p = p->next;
 }
 if(i < p->data)//在链表中间某处找到合适插入位置  
 {
   temp ->next = p;
   temp ->pre = p->pre;
   p ->pre->next = temp;
   p ->pre = temp;
   return head;
 }
 else//没有找到合适的位置,只有将数据插入到链表尾部  
 {
   p->next = temp; //遍历到链表尾部,p==NULL  
   temp ->pre = p;
   temp ->next = NULL;
   return head;
 }
}
int main()
{
 DlinkedList_Node *head;
 head = createDLink();
 printDLink(head);
 head = insertDlinkedList_Node(head,1012);
 head = deleteDlinkedList_Node(head,1991);
 printDLink(head);
}
/*****************************
运行结果如下:
please input the data:
1991
please input the data:
1992
please input the data:
2013
please input the data:
2014
please input the data:
512
please input the data:
420
please input the data:
65535

数据输入结束
正序输出双向链表:
1991 1992 2013 2014 512 420
逆序输出双向链表:
420 512 2014 2013 1992 1991

正序输出双向链表:
1012 1992 2013 2014 512 420
逆序输出双向链表:
420 512 2014 2013 1992 1012

******************************/
0
投稿

猜你喜欢

手机版 软件编程 asp之家 www.aspxhome.com