1.什么是内存泄漏?
主动申请到的内存空间没有进行内存释放,导致无内存空间可用。
2.双向链表?
双向链表(Doubly Linked List)是链表的一种,它允许我们在链表中的任何一个节点向前或
向后遍历。与单向链表相比,双向链表中的每个节点不仅存储了指向下一个节点的指针(或引
用),还存储了指向前一个节点的指针(或引用)。这种双向链接性提供了更多的灵活性,但同时
也需要更多的内存来存储额外的指针。
3.双向链表的基本结构
在双向链表中,每个节点通常包含三个基本部分:
- 数据域:存储节点的数据。
- 前驱ppre):指向链表中的前一个节点。
- 后继指针(next):指向链表中的下一个节点。
4.单项链表与双向链表区别?
单向链表只能单向访问,节点只有一个指向下一个节点的指针;而双向链表可以双向访问,
节点有两个指针,分别指向前一个和后一个节点。
5.练习
#include <stdio.h>
#include "doulink.h"
#include <stdlib.h>
#include <string.h>
//创建
Dlink_t *create_dlink()
{
Dlink_t *pdoulink = (Dlink_t *)malloc(sizeof(Dlink_t));
if(NULL == pdoulink)
{
perror("malloc fail");
return NULL;
}
pdoulink->phead = NULL;
pdoulink->clen = 0;
pthread_mutex_init(&pdoulink->mutex,NULL);
return pdoulink;
}
int is_empty_doulink(Dlink_t *pdoulink)
{
return NULL == pdoulink->phead;
}
//头插
int push_doulink_head(Dlink_t *pdoulink, DataType data)
{
Dlink_node_t *pnode = (Dlink_node_t *)malloc(sizeof(Dlink_node_t));
if(NULL == pnode)
{
perror("fail malloc");
return -1;
}
pnode->data = data;
pnode->ppre =NULL;
pnode->pnext =NULL;
if(is_empty_doulink(pdoulink))
{
pdoulink->phead = pnode;
}
else
{
pnode->pnext = pdoulink->phead;
pdoulink->phead->ppre = pnode;
pdoulink->phead= pnode;
}
pdoulink->clen++;
return 0;
}
int push_doulink_tail(Dlink_t *pdoulink,DataType data)
{
Dlink_node_t *pnode = (Dlink_node_t *)malloc(sizeof(Dlink_node_t));
if(NULL == pnode)
{
perror("fail malloc");
return -1;
}
pnode->data =data;
pnode->ppre = NULL;
pnode->pnext =NULL;
if(is_empty_doulink(pdoulink))
{
pdoulink->phead = pnode;
}
else
{
Dlink_node_t *p =pdoulink->phead;
while(p->pnext!= NULL)
{
p=p->pnext;
}
p->pnext = pnode;
pnode->ppre = p;
}
pdoulink->clen++;
return 0;
}
int pop_doulink_head(Dlink_t *pdoulink)
{
if(is_empty_doulink(pdoulink))
{
return 0;
}
Dlink_node_t *p = pdoulink->phead;
pdoulink->phead = p->pnext;
p->ppre = NULL;
free(p);
pdoulink->clen--;
return 0;
}
int pop_doulink_tail(Dlink_t *pdoulink)
{
if(is_empty_doulink(pdoulink))
{
return 0;
}
Dlink_node_t *p = pdoulink->phead;
while(p->pnext->pnext != NULL)
{
p=p->pnext;
}
free(p->pnext);
p->pnext=NULL;
pdoulink->clen--;
return 0;
}
Dlink_node_t *find_data(Dlink_t *pdoulink,char *name)
{
if(is_empty_doulink(pdoulink))
{
return NULL;
}
Dlink_node_t *p = pdoulink->phead;
while(p!= NULL)
{
if(strcmp(p->data.name,name)==0)
{
//printf("find : %s\n",p->data.name);
return p;
}
p=p->pnext;
}
return NULL;
}
int change_doulink(Dlink_t *pdoulink,char *name,int score)
{
if(is_empty_doulink(pdoulink))
{
return 0;
}
Dlink_node_t *p = find_data(pdoulink,name);
p->data.score = score;
return 0;
}
void printf_doulink(Dlink_t *pdoulink)
{
Dlink_node_t *p = pdoulink->phead;
while(p != NULL)
{
printf("[%d %s %d]\n",p->data.id, p->data.name,p->data.score);
// printf("%p ",p);
p = p->pnext;
}
printf("%d\n",pdoulink->clen);
printf("********************\n");
}
void printf_back_doulink(Dlink_t *pdoulink)
{
Dlink_node_t *p = pdoulink->phead;
while(p->pnext != NULL)
{
p = p->pnext;
}
while(p!=NULL)
{
printf("[%d %s %d]\n",p->data.id, p->data.name,p->data.score);
// printf("%p ",p);
p = p->ppre;
}
}
void destroy_dlink(Dlink_t *pdoulink)
{
while(!is_empty_doulink(pdoulink))
{
pop_doulink_head(pdoulink);
}
free(pdoulink);
}