C语言实现双向链表数据结构

本文分享了一个在Linux环境下调试成功的双向循环链表程序,包括了创建、添加、删除等基本操作,并提供了完整的源代码及执行结果,适用于学习数据结构和链表操作。

上午写了下双向循环链表的程序,主要为了学习,贴上我所调试成功的代码(Linux环境下)

function.h 头文件——包含节点结构的定义和各种操作函数的声明。

/**

* @ Copyright (C), 1993-2018, lizzcf.

* @ **
* @ File Name     : function.h
* @ Version       : Initial Draft
* @ Author        : lizzcf
* @ Created       : 2018/10/23
* @ Last Modified :
* @ Description   : s
* @ Function List : 

* @ History       :
* @ 1.Date        : 2018/10/23
* @   Author      : lizzcf
* @   Modification: Created file
* @ **

*/

#ifndef FUNCTION_H
#define FUNCTION_H

#define RET_SUCC (0)
#define RET_ERR (-1)
#define TRUE (1)
#define FALSE (0)

typedef struct tagDoubleLinkNode
{
    int data;
    struct tagDoubleLinkNode* pPre;
    struct tagDoubleLinkNode* pNext;
}node;

typedef struct tagDoubleLink
{
    int size;
    struct tagDoubleLinkNode* pHead;
    struct tagDoubleLinkNode* pTail;
    struct tagDoubleLinkNode* pCur;
}link;


//创建双向链表
link* createList(void);
//将元素添加到链表的末尾
int addBack(link* list, int data);
//将元素添加到链表前端
int addFront(link* list, int data);
//将元素添加到指定节点之后
int addAfterNode(link* list, int nodeNum, int data);
//将元素添加到指定节点之前
int addBeforeNode(link* list, int nodeNum, int data);
//将元素添加到指定数据后
int addAfterNum(link* list, int targetNum, int data);
//将元素添加到指定数据前
int addBeforeNum(link* list, int targetNum, int data);
//将元素从末端移除
int removeBack(link* list);
//将元素从前端移除
int removeFront(link* list);
//删除指定节点
int removeNode(link* list, int nodeNum);
//删除相同节点
int removeSameNode(link* list);
//打印链表
void printList(link* list);
//清空链表中所有元素
void clearList(link* list);
//销毁链表
void destroyList(link* list);

#endif
 

function.c 双向链表的源文件——包含了各种操作函数的定义。

/**

* @ Copyright (C), 1996-2018, Fotile.

* @ **
* @ File Name     : function.c
* @ Version       : Initial Draft
* @ Author        : lizzcf
* @ Created       : 2018/10/23
* @ Last Modified :
* @ Description   : s
* @ Function List :

* @ History       :
* @ 1.Date        : 2018/10/23
* @   Author      : lizzcf
* @   Modification: Created file
* @ **

*/


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

#include "function.h"
#include "print.h"

/**
* @ Prototype    : _isTail
* @ Description  : 判断当前位置是否为最后
* @ Input        : link* list
* @ Output       : 
* @ Return Value : int
* @ Calls        : 
* @ Called By    : 

* @ History         :
* @ 1.Date         : 2018/11/6
* @    Author         : lizzcf
* @    Modification : Created function
*/
int _isTail(link* list)
{
    if(list->pCur == list->pTail)
    {
        return TRUE;
    }
    return FALSE;
}

/**
* @ Prototype    : _isPre
* @ Description  : 判断当前位置是否为头
* @ Input        : link* list
* @ Output       : 
* @ Return Value : int
* @ Calls        : 
* @ Called By    : 

* @ History         :
* @ 1.Date         : 2018/11/6
* @    Author         : lizzcf
* @    Modification : Created function
*/
int _isPre(link* list)
{
    if(list->pCur == list->pHead)
    {
        return TRUE;
    }
    return FALSE;
}

/**
* @ Prototype      : _moveCurToHead
* @ Description  : 将当前位置移动到链表的开始
* @ Input          : link* list
* @ Output       : 
* @ Return Value : void
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
void _moveCurToHead(link* list)
{
    list->pCur = list->pHead;
}

/**
* @ Prototype      : _moveCurToTail
* @ Description  : 将当前位置移动到链表的最后
* @ Input          : link* list
* @ Output       : 
* @ Return Value : void
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
void _moveCurToTail(link* list)
{
    list->pCur = list->pTail;
}

/**
* @ Prototype      : _moveCurToNext
* @ Description  : 将当前位置向后移动一个位置
* @ Input          : link* list
* @ Output       : 
* @ Return Value : void
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
void _moveCurToNext(link* list)
{
    if(!_isTail(list))
    {
        list->pCur = list->pCur->pNext;
    }
}

/**
* @ Prototype      : _moveCurToPre
* @ Description  : 将当前位置向前移动一个位置
* @ Input          : link* list
* @ Output       : 
* @ Return Value : void
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
void _moveCurToPre(link* list)
{
    if(!_isPre(list))
    {
        list->pCur = list->pCur->pPre;
    }
}

/**
* @ Prototype      : _moveCurToNode
* @ Description  : 将当前位置移动到指定节点
* @ Input          : link* list, int nodeNum
* @ Output       : 
* @ Return Value : void
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
void _moveCurToNode(link* list, int nodeNum)
{
    if(nodeNum>= list->size)
    {
        _moveCurToTail(list);
        return;
    }
    if(nodeNum <= 1)
    {
        _moveCurToHead(list);
        return;
    }

    int i = 0;
    _moveCurToHead(list);
    for(i = 1; i < nodeNum; i++)
    {
        _moveCurToNext(list);
    }
}

/**
* @ Prototype    : createList
* @ Description  : 创建双向链表
* @ Input        : void
* @ Output       : 
* @ Return Value : link*
* @ Calls        : 
* @ Called By    : 
 
* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author       : lizzcf
* @   Modification : Created function
*/
link* createList(void)
{
    link* list = NULL;
    list = (link*)malloc(sizeof(link));
    if (NULL == list)
    {
        Error("Memory allocation failed!");
        return NULL;
    }

    list->pHead = NULL;
    list->pTail = NULL;
    list->pCur = NULL;
    list->size = 0;

    return list;
}

 /**
 * @ Prototype      : addBack
 * @ Description  : 将元素添加到链表的末尾
 * @ Input          : link* list, int data
 * @ Output       : 
 * @ Return Value : int
 * @ Calls          : 
 * @ Called By      : 
  
 * @ History        :
 * @ 1.Date         : 2018/11/6
 * @   Author        : lizzcf
 * @   Modification : Created function
 */
int addBack(link* list, int data)
{
    node* newNode = NULL;
    newNode = (node*)malloc(sizeof(node));
    if (NULL == newNode)
    {
        Error("Memory allocation failed!");
        return RET_ERR;
    }

    newNode->data = data;

    if(list->pTail) //链表非空
    {
        list->pTail->pNext = newNode;
        newNode->pPre = list->pTail;
    }
    else
    {
        newNode->pPre = NULL;
        list->pHead = newNode;
    }

    newNode->pNext = NULL;
    list->pTail = newNode;

    return ++list->size;
}

/**
* @ Prototype      : addFront
* @ Description  : 将元素添加到链表前端
* @ Input          : link* list, int data
* @ Output       : 
* @ Return Value : int
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
int addFront(link* list, int data)
{
    node* newNode = NULL;
    newNode = (node*)malloc(sizeof(node));
    if (NULL == newNode)
    {
        Error("Memory allocation failed!");
        return RET_ERR;
    }

    newNode->data = data;

    if(list->pHead) //链表非空
    {
        list->pHead->pPre = newNode;
        newNode->pNext = list->pHead;
    }
    else
    {
        newNode->pNext = NULL;
        list->pTail = newNode;
    }

    newNode->pPre = NULL;
    list->pHead = newNode;

    return ++list->size;
}

/**
* @ Prototype      : addAfterNode
* @ Description  : 将元素添加到指定节点之后
* @ Input          : link* list, int nodeNum, int data
* @ Output       : 
* @ Return Value : int
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
int addAfterNode(link* list, int nodeNum, int data)
{
    if(nodeNum >= list->size)
    {
        return addBack(list, data);
    }    
    if(nodeNum <= 0)
    {
        return addFront(list, data);
    }

    int i = 0;
    node* temp = NULL;
    node* newNode = NULL;
    newNode = (node*)malloc(sizeof(node));
    if (NULL == newNode)
    {
        Error("Memory allocation failed!");
        return RET_ERR;
    }

    newNode->data = data;

    _moveCurToNode(list, nodeNum);

    temp = list->pCur->pNext;
    list->pCur->pNext = newNode;
    newNode->pPre = list->pCur;
    newNode->pNext = temp;
    temp->pPre = newNode;

    return ++list->size;
}

/**
* @ Prototype      : addBeforeNode
* @ Description  : 将元素添加到指定节点之前
* @ Input          : link* list, int nodeNum, int data
* @ Output       : 
* @ Return Value : int
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
int addBeforeNode(link* list, int nodeNum, int data)
{
    if(nodeNum > list->size)
    {
        return addBack(list, data);
    }    
    if(nodeNum <= 1)
    {
        return addFront(list, data);
    }

    int i = 0;
    node* temp = NULL;
    node* newNode = NULL;
    newNode = (node*)malloc(sizeof(node));
    if (NULL == newNode)
    {
        Error("Memory allocation failed!");
        return RET_ERR;
    }

    newNode->data = data;

    _moveCurToNode(list, nodeNum);

    temp = list->pCur->pPre;
    list->pCur->pPre = newNode;
    newNode->pNext = list->pCur;
    newNode->pPre = temp;
    temp->pNext = newNode;

    return ++list->size;
}

/**
* @ Prototype      : addAfterNum
* @ Description  : 将元素添加到指定数据后
* @ Input          : link* list, int targetNum, int data
* @ Output       : 
* @ Return Value : int
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
int addAfterNum(link* list, int targetNum, int data)
{
    if(!list->size)
    {
        return list->size;
    }

    int i = 0;
    for(i = 1; i <= list->size; i++)
    {
        if(1 == i)
        {
            _moveCurToHead(list);
        }
        else
        {
            _moveCurToNext(list);
        }

        if(list->pCur->data == targetNum)
        {
            addAfterNode(list, i, data);
            return list->size;
        }
    }

    Error("Can not find the target num, add failed!");
    return list->size;
}

/**
* @ Prototype      : addBeforeNum
* @ Description  : 将元素添加到指定数据前
* @ Input          : link* list, int targetNum, int data
* @ Output       : 
* @ Return Value : int
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
int addBeforeNum(link* list, int targetNum, int data)
{
    if(!list->size)
    {
        return list->size;
    }

    int i = 0;
    for(i = 1; i <= list->size; i++)
    {
        if(1 == i)
        {
            _moveCurToHead(list);
        }
        else
        {
            _moveCurToNext(list);
        }

        if(list->pCur->data == targetNum)
        {
            addBeforeNode(list, i, data);
            return list->size;
        }
    }

    Error("Can not find the target num, add failed!");
    return list->size;
}

/**
* @ Prototype      : removeBack
* @ Description  : 将元素从末端移除
* @ Input          : link* list
* @ Output       : 
* @ Return Value : int
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
int removeBack(link* list)
{
    if(!list->size)
    {
        return list->size;
    }

    node* temp = NULL;
    temp = list->pTail;

    if(list->pHead == list->pTail)
    {
        list->pHead = NULL;
        list->pTail = NULL;
        list->pCur = NULL;
    }
    else
    {
        list->pTail = list->pTail->pPre;
        list->pTail->pNext = NULL;
    }

    free(temp);
    return --list->size;
}

/**
* @ Prototype      : removeFront
* @ Description  : 将元素从前端移除
* @ Input          : link* list
* @ Output       : 
* @ Return Value : int
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
int removeFront(link* list)
{
    if(!list->size)
    {
        return list->size;
    }

    node* temp = NULL;
    temp = list->pHead;

    if(list->pHead == list->pTail)
    {
        list->pHead = NULL;
        list->pTail = NULL;
        list->pCur = NULL;
    }
    else
    {
        list->pHead= list->pHead->pNext;
        list->pHead->pPre = NULL;
    }

    free(temp);
    return --list->size;
}

/**
* @ Prototype      : removeNode
* @ Description  : 删除指定节点
* @ Input          : link* list, int nodeNum
* @ Output       : 
* @ Return Value : int
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
int removeNode(link* list, int nodeNum)
{
    if(!list->size)
    {
        return list->size;
    }
    if(nodeNum >= list->size)
    {
        return removeBack(list);
    }
    if(nodeNum <= 1)
    {
        return removeFront(list);
    }

    node* temp = NULL;
    _moveCurToNode(list, nodeNum);
    temp = list->pCur;

    list->pCur->pPre->pNext = list->pCur->pNext;
    list->pCur->pNext->pPre = list->pCur->pPre;
    list->pCur = NULL;

    free(temp);
    return --list->size;
}

/**
* @ Prototype      : removeSameNode
* @ Description  : 删除相同节点
* @ Input          : link* list
* @ Output       : 
* @ Return Value : int
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
int removeSameNode(link* list)
{
    if(!list->size)
    {
        return list->size;
    }

    int i = 0;
    int j = 0;
    int temp = 0;

    for(i = 1; i <= list->size; i++)
    {
        _moveCurToNode(list, i);
        temp = list->pCur->data;
        for(j = i + 1; j <= list->size; j++)
        {
            _moveCurToNode(list, j);
            if(temp == list->pCur->data)
            {
                removeNode(list, j);
                j--;
            }
        }
    }

    return list->size;
}


/**
* @ Prototype      : printList
* @ Description  : 打印链表
* @ Input          : link* list
* @ Output       : 
* @ Return Value : void
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
void printList(link* list)
{
    int i = 0;
    _moveCurToHead(list);
    printf("List:");
    for(i = 0; i < list->size; i++)
    {
        printf("%d ", list->pCur->data);
        _moveCurToNext(list);
    }
    printf("\n");
}

/**
* @ Prototype      : clearList
* @ Description  : 清空链表中所有元素
* @ Input          : link* list
* @ Output       : 
* @ Return Value : void
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
void clearList(link* list)
{
    while(removeBack(list));
}

/**
* @ Prototype      : destroyList
* @ Description  : 销毁链表
* @ Input          : link* list
* @ Output       : 
* @ Return Value : void
* @ Calls          : 
* @ Called By      : 

* @ History        :
* @ 1.Date         : 2018/11/6
* @   Author        : lizzcf
* @   Modification : Created function
*/
void destroyList(link* list)
{
    clearList(list);
    free(list);
}
 

main.c main函数源文件

/**

* @ Copyright (C), 1993-2018, lizzcf.

* @ **
* @ File Name     : main.c
* @ Version       : Initial Draft
* @ Author        : lizzcf
* @ Created       : 2018/10/23
* @ Last Modified :
* @ Description   : s
* @ Function List : main

* @ History       :
* @ 1.Date        : 2018/10/23
* @   Author      : lizzcf
* @   Modification: Created file
* @ **

*/


#include <string.h>
#include <stdio.h>
#include "function.h"
#include "print.h"

int main()
{
    link* list = NULL;
    list = createList();

    addBack(list, 1);
    addFront(list, 6);
    addAfterNode(list, 1, 8);
    addBeforeNode(list, 2, 5);
    addBeforeNode(list, 2, 5);
    addBeforeNode(list, 2, 5);
    addBeforeNode(list, 2, 5);
    printList(list);
    removeNode(list, 3);
    printList(list);
    removeSameNode(list);
    printList(list);
    addAfterNum(list, 8, 7);
    printList(list);
    addBeforeNum(list, 7, 9);
    printList(list);
    Debug("List size = %d.", list->size);
    clearList(list);

    return RET_SUCC;
}

以下是执行结果:

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值