循環鏈表C語言實現

按照單鏈表的設計,稍加改動。和單向鏈表不同的地方,頭節點不指向NULL,而是指向本身head
循環鏈表的判滿 1)判斷next是否是頭結點,2)判斷sizenode

/*
 * CycleLinkList.h
 *
 *  Created on: 2019年7月24日
 *      Author: Administrator
 */

#ifndef SRC_CYCLELINKLIST_H_
#define SRC_CYCLELINKLIST_H_

#define CIRCLELINKLIST_TRUE 1
#define CIRCLELINKLIST_FALSE 0


/**
 * 一、循環鏈表,帶頭節點,初始化的時候,和單向鏈表不同的地方,頭節點不指向NULL,而是指向本身head
 * 二、循環鏈表的判滿 1)判斷next是否是頭結點,2)判斷size
 * */

//鏈表的小節點
typedef struct CIRCLELINKNODE {
    struct CIRCLELINKNODE *next;
}CircleLinkNode;


//結構體
typedef struct CIRCLELINKLIST {
    CircleLinkNode head;
    int size;
}CircleLinkList;

//比較回調
typedef int(*COMPARENODE)(CircleLinkNode *, CircleLinkNode *);

typedef void(*PRINTNODE)(CircleLinkNode *);

//API
//建立一個循環鏈表
CircleLinkList *Init_CircleLinkList();

//插入
void Insert_CircleLinkList(CircleLinkList *clist, int pos, CircleLinkNode *data);

//獲取第一個元素
CircleLinkNode *Front_CircleLinkList(CircleLinkList *clist);

//根據位置刪除
void RemoveByPos_CircleLinkList(CircleLinkList *clist, int pos);

//根據值刪除
void RemoveByValue_CircleLinkList(CircleLinkList *clist, CircleLinkNode *data, COMPARENODE compare);


//得到鏈表的長度
int Size_CircleLinkList(CircleLinkList *clist);

//判斷是否爲空
int IsEmpty_CircleLinkList(CircleLinkList *clist);
//查找
int Find_CircleLinkList(CircleLinkList *clist, CircleLinkNode *data, COMPARENODE compare);

//打印
void Print_CircleLinkList(CircleLinkList *clist, PRINTNODE print);

//釋放內存
void FreeSpace_CircleLinkList(CircleLinkList *clist);


#endif /* SRC_CYCLELINKLIST_H_ */
/*
 * CylceLinkList.c
 *
 *  Created on: 2019年7月24日
 *      Author: Administrator
 */
#include "CycleLinkList.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>


//建立一個循環鏈表
CircleLinkList *Init_CircleLinkList() {
    CircleLinkList *clist = (CircleLinkList *)malloc(sizeof(CircleLinkNode));
    clist->head.next = &(clist->head);
    clist->size = 0;
    return clist;
}

//插入
void Insert_CircleLinkList(CircleLinkList *clist, int pos, CircleLinkNode *data) {
    if(clist == NULL){
        return;
    }

    if(data == NULL){
        return;
    }

    if(pos < 0 || pos > clist->size){
        pos = clist->size;
    }

    //根據位置查找節點
    //操做指針的時候必定要引入一個指針變量,否則極可能改變指針
    CircleLinkNode *pCurrent = &(clist->head);
    for(int i = 0; i < pos; i++){
        pCurrent = pCurrent->next;
    }
    data->next = pCurrent->next;
    pCurrent->next = data;

    clist->size++;
}

//獲取第一個元素
CircleLinkNode *Front_CircleLinkList(CircleLinkList *clist) {
    return clist->head.next;
}

//根據位置刪除
void RemoveByPos_CircleLinkList(CircleLinkList *clist, int pos) {
    if(clist == NULL){
        return;
    }

    if(pos < 0 || pos>= clist->size){
        return;
    }
    //根據pos 找節點
    //輔助指針變量
    CircleLinkNode *pCurrent = &(clist->head);
    for(int i = 0; i < pos; i++){
        pCurrent = pCurrent->next;
    }

    //緩存當前節點的下一個節點
    CircleLinkNode *pNext = pCurrent->next;
    pCurrent->next = pNext->next;

    clist->size--;
}


//根據值刪除
void RemoveByValue_CircleLinkList(CircleLinkList *clist, CircleLinkNode *data, COMPARENODE compare) {
    if(clist == NULL){
        return;
    }

    if(data == NULL){
        return;
    }

    //這是循環鏈表
    CircleLinkNode *pPrev = &(clist->head);//找到相等打的元素值時,存儲要刪除的元素的前驅節點
    CircleLinkNode *pCurrent = clist->head.next;//用來記錄 要刪除的元素的結點
    for(int i = 0; i < clist->size; i++){
        if(compare(pCurrent, data) == CIRCLELINKLIST_TRUE){//找點操做
            pPrev->next = pCurrent->next;//刪除操做
            break;
        }
        pPrev = pCurrent;//比較指針後移
        pCurrent = pCurrent->next;//遊標指針後移
    }
    free(pCurrent);
    clist->size--;
}


//得到鏈表的長度
int Size_CircleLinkList(CircleLinkList *clist) {
    return clist->size;
}

//判斷是否爲空
int IsEmpty_CircleLinkList(CircleLinkList *clist) {
    if(clist->size == 0){
        return CIRCLELINKLIST_TRUE;
    }
    return CIRCLELINKLIST_FALSE;
}

//查找
int Find_CircleLinkList(CircleLinkList *clist, CircleLinkNode *data, COMPARENODE compare) {
    if(clist == NULL){
            return -1;
        }

    if(data == NULL){
        return -1;
    }
    CircleLinkNode *pCurrent = clist->head.next;
    int flag = -1;
    for(int i = 0; i < clist->size; i++){
        if(compare(pCurrent, data) == CIRCLELINKLIST_TRUE){
            flag = i;
            break;
        }
        pCurrent = pCurrent->next;
    }

    return flag;
}

//打印
void Print_CircleLinkList(CircleLinkList *clist, PRINTNODE print) {
    if(clist == NULL){
        return;
    }
    //輔助指針變量
    CircleLinkNode *pCurrent = clist->head.next;
    for(int i = 0; i < clist->size; i++){
        if(pCurrent == pCurrent->next){
            pCurrent = pCurrent->next;
        }
        print(pCurrent);
        pCurrent = pCurrent->next;
    }
}

//釋放內存
void FreeSpace_CircleLinkList(CircleLinkList *clist) {
    if(clist == NULL){
        return;
    }
    free(clist);
}
/*
 * main.c
 *
 *  Created on: 2019年7月24日
 *      Author: Administrator
 */


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

typedef struct PERSON{
    CircleLinkNode node;
    char name[64];
    int age;
    int score;
}Person;


void MyPrint(CircleLinkNode *data){
    Person *p = (Person *)data;
    printf("name: %s , age: %d, score: %d \n", p->name, p->age, p->score);
}

int MyCompare(CircleLinkNode *data1, CircleLinkNode *data2){
    Person *p1 = (Person *)data1;
    Person *p2 = (Person *)data2;

    if(strcmp(p1->name, p2->name) == 0 && p1->age == p2->age && p1->score == p2->score){
        return CIRCLELINKLIST_TRUE;
    }
}

int main(){
    printf("循環鏈表  \n");
    //建立循環鏈表
    CircleLinkList *clist = Init_CircleLinkList();

    //建立數據
    Person p1, p2, p3, p4, p5;
    strcpy(p1.name, "Jarvis");
    strcpy(p2.name, "Marvis");
    strcpy(p3.name, "Harvis");
    strcpy(p4.name, "Larvis");
    strcpy(p5.name, "Karvis");

    p1.age = 21;
    p2.age = 22;
    p3.age = 23;
    p4.age = 24;
    p5.age = 25;

    p1.score = 91;
    p2.score = 92;
    p3.score = 93;
    p4.score = 94;
    p5.score = 95;


    Insert_CircleLinkList(clist, 0, (CircleLinkNode *)&p1);
    Insert_CircleLinkList(clist, 1, (CircleLinkNode *)&p2);
    Insert_CircleLinkList(clist, 2, (CircleLinkNode *)&p3);
    Insert_CircleLinkList(clist, 3, (CircleLinkNode *)&p4);
    Insert_CircleLinkList(clist, 4, (CircleLinkNode *)&p5);

    //打印
    Print_CircleLinkList(clist, MyPrint);

    //刪除
    Person pDel;
    strcpy(pDel.name, "Marvis");
    pDel.age = 22;
    pDel.score = 92;

    RemoveByValue_CircleLinkList(clist, (CircleLinkNode *)&pDel, MyCompare);

    //打印
    printf("刪除後打印 \n");
    Print_CircleLinkList(clist, MyPrint);
    //釋放內存
    FreeSpace_CircleLinkList(clist);
    system("pause");
    return 0;
}
循環鏈表  
name: Jarvis , age: 21, score: 91 
name: Marvis , age: 22, score: 92 
name: Harvis , age: 23, score: 93 
name: Larvis , age: 24, score: 94 
name: Karvis , age: 25, score: 95 
刪除後打印 
name: Jarvis , age: 21, score: 91 
name: Harvis , age: 23, score: 93 
name: Larvis , age: 24, score: 94 
name: Karvis , age: 25, score: 95
相關文章
相關標籤/搜索