栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > C/C++/C#

动态链表整理

C/C++/C# 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

动态链表整理

动态链表 链表的定义
  • 链表是一种物理存储单元上非连续、非顺序的存储结构,数据元素的逻辑顺序是通过链表中的指针链接次序实现的
前置知识
  • 主要涉及结构体,指针,以及函数的知识
链表的储存
  • 本文章主要采用的是链式储存的方法

  • 需要定义一个结构体,包括数据以及之战两部分

    struct node 
    { 
        int data; //储存当前结点的数值
        struct node * next; //存放下一个结点的地址
    }; 
    
  • 为了方便之后操作我们可以用typedef对结构体类型重命名

    typedef struct node 
    { 
        int data; 
        struct node * next; 
    } Node; 
    
  • 接下来我们试在主函数中,创建空链表

     Node * head = NULL; //指针指向空
    
  • 最后要释放连接

    void freeList(Node ** pHead) 
    { 
        Node * p = *pHead; 
        Node * pre; 
        while (p != NULL) 
        { 
            pre = p; p = p->next;
            free(pre); 
        }
        *pHead = NULL; 
    }
    
按顺序插入数据(尾插)
  • 大致思路为将前一个结点的指针指向新结点
  • 新结点的指针应当指向空结点(成为尾节点)
  • 注意:当原有链表为空时,要将主函数中的头结点指向新结点
//因为要对头结点进行修改,所以传入的时头节点的地址
//头结点地址,加入的数据
void push_back_list(Node ** phead, int data) 
{ 
    //动态链表要申请动态的内存 
    Node * newNode = (Node *)malloc(sizeof(Node)); 
    newNode->data = data; 
    newNode->next = NULL; 
    // 判断原链表是否为空链表 
    if (*phead == NULL) 
    {  
        *phead = newNode; 
    } 
    else 
    { 
        Node * temp = *pHead; 
        // 循环判断寻找尾结点
        while (temp->next != NULL) 
            temp = temp->next; // 原链表尾节点指向新节点 
        temp->next = newNode; 
    } 
}

常见链表操作 链表元素统计与打印
  • 主要依靠循环遍历
void printList(Node * head) 
{ 
    Node * p;
    for (p=head; p!=NULL; p=p->next) 
        printf("%d ", p->data); //等价于 `*p.`
    puts(""); 
}

int size_list(Node *phead)
{
    int cnt = 0;
    Node *p;
    for(p = phead; p != NULL; p = p->next)
        cnt ++;
    
    return cnt;
}
插入结点
  • 含n个结点的链表有n+1个位置可以插入,插到n位置需要n + 1次(找到插入位置之前的结点)
  • 先将新结点的指针指向后结点再将前结点的指针指向新结点
    • 顺序反过来会产生环,而且会丢失数据
//头结点地址,插入位置,插入数据
void insert_list(Node **phead,int index, int date)
{
    if(index < 0 || index > size_list(*phead)) 
        return;

    Node *newNode;
    newNode = (Node*)malloc(sizeof(Node));
    newNode -> next = NULL;
    newNode -> data = date;
    
    //特判插入头结点时
    if(index == 0)
    {
        newNode->next = *phead;
        *phead = newNode;
        return;
    }

    Node *p;
    p = *phead;
    int i;
    for(i = 0; i < index - 1; i ++)
        p = p ->next;
    newNode->next = p->next;
    p->next = newNode;
}
删除结点(删除所有出现的某个数)
  • 将需要删除结点a的前一个结点的指针指向a后的一个结点

  • 删除头结点时需特殊处理(不需要再找它前面的结点)

  • 删除第一次出现的某个数思想类似,将循环稍加改动即可

//头结点地址以及需要删除的数字
//随删随释放内存
void delete_list(Node **phead, int date)
{
    Node *p = *phead; 

    while(p->next != NULL)
    {
        if(p->next->data == date)
        {
            Node *t = p->next;
            p ->next = t->next;
            free(t);
        }
        else p = p->next;
    }

    p = *phead;
    if(p->data == date)
    {
        *phead = p->next;
        free(p);
    }
}
t = t->next;
            free(t);
        }
        else p = p->next;
    }

    p = *phead;
    if(p->data == date)
    {
        *phead = p->next;
        free(p);
    }
}
转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/913292.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号