双链表

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

typedef struct {
    int id;
}Elemtype;
typedef struct st{
    Elemtype data;
    struct st *prior,*next;
}DNode,*DLinkList;
bool InitDLinkList(DLinkList *L);
bool InsertDLinkList(DNode *p,DNode *s);
bool DeleteNode(DNode *p);
void DestoryList(DLinkList *L);
void skimDLinkList(DLinkList *L,DNode *q);

int main(){
    Elemtype a={1},b={2},c={3};
    DNode *d=(DNode *)malloc(sizeof(DNode)),*e=(DNode *)malloc(sizeof(DNode)),*f=(DNode *)malloc(sizeof(DNode));
    d->data=a;
    e->data=b;
    f->data=c;
    DLinkList *L= (DLinkList *) malloc(sizeof(DLinkList));
    *L = (DNode *) malloc(sizeof(DNode *));
    InitDLinkList(L);
    InsertDLinkList(*L, d);
    InsertDLinkList(*L,e);
    DeleteNode(e);
    InsertDLinkList(d,f);
    DeleteNode(f);
    InsertDLinkList(*L,e);
    DestoryList(L);

    return 0;
}

bool InitDLinkList(DLinkList *L){
    /*下面两行代码并不能初始化,因为传进函数之后,只有链表指针成功初始化了。而指针的指针并没有成功的初始化*/
//    L = (DLinkList *) malloc(sizeof(DLinkList));//L是指针的指针,如果指针没有指向一个已有的变量,那么指针指向的地方必须要malloc,否则会发生指针乱指的情况
//    *L = (DNode *) malloc(sizeof(DNode *));//L是指针的指针,因此*L也是一个指针,指向的地方也要malloc
    if (*L == NULL)//内存不足,分配失败

        return false;
    (*L)->next=NULL;
    (*L)->prior=NULL;
    return true;
}

//在p结点之后插入s结点
bool InsertDLinkList(DNode *p,DNode *s){//p<->s<->q 分别修改p,s,q;
    if (p==NULL || s==NULL)//防止空指针错误
        return false;
    if (p->next==NULL){//如果p的下一个为空的话,执行以下语句
        s->next=p->next;
        p->next=s;
        s->prior=p;
        return true;
    }
    /*如果p的下一个为空的话,下面代码会发生空指针错误*/
    DNode *q=p->next;
    s->next = q;
    s->prior = p;
    p->next = s;
    q->prior = s;
    return true;
}

//删除p结点
bool DeleteNode(DNode *p){//修改p前面和后面结点就可以了
    /*下面两个if是防止空指针用的*/
    if (p==NULL)
        return false;
    if (p->next==NULL){//p是最后一个结点,只需要修改前面那个就行了
        p->prior->next=NULL;
        free(p);
        return true;
    }
    p->prior->next=p->next;
    p->next->prior=p->prior;
    free(p);//释放p的空间,这个很重要,在大型项目里面如果不释放会使得内存不足
    return true;
}

//销毁整个链表
void DestoryList(DLinkList *L){
    while ((*L)->next!=NULL){
        DeleteNode((*L)->next);//循环删除L后面的那个结点
    }
    free(*L);//最后free L
    L=NULL;
}

//遍历整个链表
void skimDLinkList(DLinkList *L,DNode *q){
    DNode *p=*L;
    while (p!=NULL){//后向遍历
        p=p->next;
    }

    while (q->next!=NULL){//q是最后一个结点,这是前向遍历,跳过头结点
        q = q->next;
    }



}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值