c语言数据结构 -单向循环链表

在这里插入图片描述

#include "CircylarLinkedlists.h"

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

void MyPrint(CircylarLinkNode*);
int MyCompare(CircylarLinkNode*, CircylarLinkNode*);

void test01();
void test02();
void test03();


int main(int argc, char **argv){
    
    test03();
    
    return 0;
}

void test01(){
    
    CircylarLinkList* clist = Init_CircylarLinkList();

    Person p1, p2, p3, p4, p5;
    strcpy(p1.name, "aaa");
    strcpy(p2.name, "bbb");
    strcpy(p3.name, "ccc");
    strcpy(p4.name, "ddd");
    strcpy(p5.name, "eee");

    p1.age = 10;
    p2.age = 20;
    p3.age = 30;
    p4.age = 40;
    p5.age = 50;

    p1.score = 50;
    p2.score = 60;
    p3.score = 70;
    p4.score = 80;
    p5.score = 90;

    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p1);
    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p2);
    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p3);
    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p4);
    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p5);


    Print_CircylarLinkList(clist, MyPrint);

    FreeSpace_CircylarLinkList(clist);
}   



void test02(){
    
    CircylarLinkList* clist = Init_CircylarLinkList();

    Person p1, p2, p3, p4, p5;
    strcpy(p1.name, "aaa");
    strcpy(p2.name, "bbb");
    strcpy(p3.name, "ccc");
    strcpy(p4.name, "ddd");
    strcpy(p5.name, "eee");

    p1.age = 10;
    p2.age = 20;
    p3.age = 30;
    p4.age = 40;
    p5.age = 50;

    p1.score = 50;
    p2.score = 60;
    p3.score = 70;
    p4.score = 80;
    p5.score = 90;

    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p1);
    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p2);
    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p3);
    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p4);
    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p5);


    Print_CircylarLinkList(clist, MyPrint);

    Person pDel;
    strcpy(pDel.name, "ccc");
    pDel.age = 30;
    pDel.score = 70;

    RemoveByVal_CircylarLinkList(clist, (CircylarLinkNode*)&pDel, MyCompare);


    Print_CircylarLinkList(clist, MyPrint);

    FreeSpace_CircylarLinkList(clist);
}   
void test03(){
    
    CircylarLinkList* clist = Init_CircylarLinkList();

    Person p1, p2, p3, p4, p5;
    strcpy(p1.name, "aaa");
    strcpy(p2.name, "bbb");
    strcpy(p3.name, "ccc");
    strcpy(p4.name, "ddd");
    strcpy(p5.name, "eee");

    p1.age = 10;
    p2.age = 20;
    p3.age = 30;
    p4.age = 40;
    p5.age = 50;

    p1.score = 50;
    p2.score = 60;
    p3.score = 70;
    p4.score = 80;
    p5.score = 90;

    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p1);
    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p2);
    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p3);
    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p4);
    Insert_CircylarLinkList(clist, 100, (CircylarLinkNode*)&p5);


    Print_CircylarLinkList(clist, MyPrint);

    RemoveByPos_CircylarLinkList(clist, 2);


    Print_CircylarLinkList(clist, MyPrint);

    FreeSpace_CircylarLinkList(clist);
}   


void MyPrint(CircylarLinkNode* data){
    Person* p = (Person*) data;

    printf("name: %s \t age: %d \t score: %d\n", p->name, p->age, p->score);
}
int MyCompare(CircylarLinkNode* node1, CircylarLinkNode* node2){

    Person* p1 = (Person*) node1;
    Person* p2 = (Person*) node2;

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

    return CIRCYLARTLINKLIST_FALSE;
}
#include "CircylarLinkedlists.h"


// 1. 初始化函数
CircylarLinkList* Init_CircylarLinkList(){

    CircylarLinkList* clist = (CircylarLinkList*)malloc(sizeof(CircylarLinkList));

    clist->head.next = &(clist->head); 
    clist->size = 0;

    return clist;
}

// 2. 插入函数(插入位置,插入的数据)
void Insert_CircylarLinkList(CircylarLinkList* clist, int pos, CircylarLinkNode* data){
    if(clist == NULL){
        return;
    }
    if(data == NULL){
        return;
    }
    if(pos < 0 || pos > clist->size){
        pos = clist->size;
    }

    // 查找前一个节点
    CircylarLinkNode* pCurrent = &(clist->head); 
    for(int i = 0; i < pos; i++){
        pCurrent = pCurrent->next; 
    }

    // 入链表
    data->next = pCurrent->next;
    pCurrent->next = data;

    clist->size++;
}

// 3. 获得第一个元素
CircylarLinkNode* Front_CircylarLinkList(CircylarLinkList* clist){
    return clist->head.next;
}

// 4. 根据位置删除
void RemoveByPos_CircylarLinkList(CircylarLinkList* clist, int pos){
    if(clist == NULL){
        return;
    }
    if(pos < 0 || pos >= clist->size){
        return;
    }

    // 查找前一个节点
    CircylarLinkNode* pCurrent = &(clist->head); 
    for(int i = 0; i < pos; i++){
        pCurrent = pCurrent->next; 
    }

    // 删除操作,这里不需要 free 操作,因为这个 CircylarLinkNode 并不是我们通过手动来分配内存的.
    pCurrent->next = pCurrent->next->next;

    clist->size--;
}

// 5. 根据元素值来删除
void RemoveByVal_CircylarLinkList(CircylarLinkList* clist, CircylarLinkNode* data, COMPARENODE compare){
    if(clist == NULL){
        return;
    }
    if(data == NULL){
        return;
    }

    CircylarLinkNode* pPrevious = &(clist->head);
    CircylarLinkNode* pCurrent = clist->head.next;
    // while(pCurrent != NULL){
    //     if(compare(pCurrent, data) == 0){
            
    //     }
    //     // next 节点
    //     pCurrent = pCurrent->next;
    // }
    for (int i = 0; i < clist->size; i++){
        if (compare(pCurrent, data) == CIRCYLARTLINKLIST_TRUE)
        {
            // 删除
            pPrevious->next = pCurrent->next;

            clist->size--;
         
            break;
        }
        pPrevious = pCurrent;
        pCurrent = pPrevious->next;
    }
}

// 6. 获得链表的长度
int Size_CircylarLinkList(CircylarLinkList* clist){
    return clist->size;
}

// 7. 查找元素
int Find_CircylarLinkList(CircylarLinkList* clist, CircylarLinkNode* data, COMPARENODE compare){
    if(clist == NULL){
        return -1;
    }
    if(data == NULL){
        return -1;
    }

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

// 8. 打印链表
void Print_CircylarLinkList(CircylarLinkList* clist, PRINTNODE print){
    if(clist == NULL){
        return;
    }

    CircylarLinkNode* pCurrent = clist->head.next;
    for(int i = 0; i < clist->size; i++){ //
        print(pCurrent);
        pCurrent = pCurrent->next;
    }
    printf("---------------------------------\n");
    
    // 打印多遍
    // for(int i = 0; i < clist->size * 3; i++){ 
    //     if(pCurrent == &(clist->head)){
    //         pCurrent = pCurrent->next;
    //         printf("---------------------------------\n");
    //     }
    //     print(pCurrent);
    //     pCurrent = pCurrent->next;
    // }
}

// 9. 释放内存
void FreeSpace_CircylarLinkList(CircylarLinkList* clist){
    if(clist == NULL){
        return;
    }

    free(clist);
}

// 10. 判断是否为空
int IsEmpty_CircylarLinkList(CircylarLinkList* clist){
    if(clist->size == 0){
        return CIRCYLARTLINKLIST_TRUE;
    }
    return CIRCYLARTLINKLIST_FALSE;
}

#ifndef CIRCYLAR_LINKED_LISTS_SINGLE_H
#define CIRCYLAR_LINKED_LISTS_SINGLE_H


#include "stdio.h"
#include "stdlib.h"
#include "string.h"

/**
 * 单向循环链表:每个节点都有一个数据域和一个指针域,这个和单向链表是一致的。但是
 * 不一样的地方是,单向循环链表的最后一个节点的指针域不为NULL,它指向头节点也可以
 * 指向第一个有效的数据节点。这些都是单向循环链表,我们一般让其指向头结点
 * 
 * 在初始化的时候,应该将头结点的next域指向自己
 * 
 * 判断链表末尾的方式:
 * 1. 节点 next 是否等于 头结点 ==> 表示该链表结束
 * 2. 通过维护 size() 来判断是否 是该链表结束标志
 */

// 链表的挂钩
typedef struct CIRCYLARLINKNODE{
    struct CIRCYLARLINKNODE* next;
}CircylarLinkNode;


// 链表的结构体:保存的就是关于该链表的一些详细信息
typedef struct CIRCYLARLINKLIST{
    CircylarLinkNode head;
    int size;
}CircylarLinkList;

#define CIRCYLARTLINKLIST_TRUE  1
#define CIRCYLARTLINKLIST_FALSE 0

// 当两个元素相同的话,返回0;否则返回-1
typedef int(*COMPARENODE)(CircylarLinkNode*, CircylarLinkNode*); // 比较的回调函数

typedef void(*PRINTNODE)(CircylarLinkNode*);

// APIs

// 1. 初始化函数
CircylarLinkList* Init_CircylarLinkList();

// 2. 插入函数(插入位置,插入的数据)
void Insert_CircylarLinkList(CircylarLinkList* clist, int pos, CircylarLinkNode* data);

// 3. 获得第一个元素
CircylarLinkNode* Front_CircylarLinkList(CircylarLinkList* clist);

// 4. 根据位置删除
void RemoveByPos_CircylarLinkList(CircylarLinkList* clist, int pos);

// 5. 根据元素值来删除
void RemoveByVal_CircylarLinkList(CircylarLinkList* clist, CircylarLinkNode* data, COMPARENODE compare);

// 6. 获得链表的长度
int Size_CircylarLinkList(CircylarLinkList* clist);

// 7. 查找元素
int Find_CircylarLinkList(CircylarLinkList* clist, CircylarLinkNode* data, COMPARENODE compare);

// 8. 打印链表
void Print_CircylarLinkList(CircylarLinkList* clist, PRINTNODE print);

// 9. 释放内存
void FreeSpace_CircylarLinkList(CircylarLinkList* clist);

// 10. 判断是否为空
int IsEmpty_CircylarLinkList(CircylarLinkList* clist);

#endif

# commands.txt
gcc -fPIC -shared CircylarLinkedlists.c -o libcircylarLinkedlists.so
gcc main.c -o main -L ./ -lcircylarLinkedlists -Wl,-rpath ./
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值