循环链表的C风格实现(单向)
头文件:
#ifndef _CIRCLELIST_H_
#define _CIRCLELIST_H_
typedef void CircleList; // typedef struct _tag_CircleListNode
{
struct _tag_CircleListNode* next;
}CircleListNode; //创建一个循环链表
CircleList* CircleList_Create();
//删除一个循环链表
void CircleList_Destroy(CircleList* list);
//清空一个循环链表
void CircleList_Clear(CircleList* list);
//返回链表的长度
int CircleList_Length(CircleList* list);
//在POS位置插入一个节点
int CircleList_Insert(CircleList* list, CircleListNode* node, int pos);
//获取POS位置节点的信息
CircleListNode* CircleList_Get(CircleList* list, int pos);
//删除POS位置的节点
CircleListNode* CircleList_Delete(CircleList* list, int pos); ////与游标相关的函数
//删除游标所指的位置节点
CircleListNode* CircleList_DeleteNode(CircleList* list, CircleListNode* node);
//重置游标位置
CircleListNode* CircleList_Reset(CircleList* list);
//当前游标位置
CircleListNode* CircleList_Current(CircleList* list);
//游标的NEXT域
CircleListNode* CircleList_Next(CircleList* list); #endif
CPP文件:
#include "circleList.h"
#include <iostream> using namespace std; //这个为头链表头
typedef struct _tag_CircleList
{
CircleListNode header;
CircleListNode* slider;
int length;
}tagCircleList; //创建一个循环链表
CircleList* CircleList_Create()
{
tagCircleList* ret = (tagCircleList*)malloc(sizeof(tagCircleList)); //分配内存
if (ret == NULL)
{
return NULL;
} //初始化
ret->header.next = NULL;
ret->length = ;
ret->slider = NULL; return ret;
} //删除一个循环链表
void CircleList_Destroy(CircleList* list)
{
if (list = NULL)
{
return;
}
//释放内存
free(list);
return;
} //清空一个循环链表
void CircleList_Clear(CircleList* list)
{
tagCircleList* sList = NULL;
sList = (tagCircleList*)list;
if (sList == NULL)
{
return ;
}
//重置为初始化状态
sList->header.next = NULL;
sList->length = ;
sList->slider = NULL;
return;
} //返回链表的长度
int CircleList_Length(CircleList* list)
{
tagCircleList* sList = NULL;
sList = (tagCircleList*)list;
int ret = -;
//异常处理
if (list == NULL)
{
return ret;
} return sList->length;
} //在POS位置插入一个节点
int CircleList_Insert(CircleList* list, CircleListNode* node, int pos)
{
tagCircleList* sList = NULL;
sList = (tagCircleList*)list;
int ret = -;
//异常处理
if(list == NULL || node == NULL || pos<)
{
return ret;
}
//临时变量Current
CircleListNode* Current = (CircleListNode*)sList; for(int i = ; (i < pos) && (Current->next != NULL); i++)
{
Current = Current->next;
} node->next = Current->next;
Current->next = node; //当长度为0时 游标指向node
if (sList->length == )
{
sList->slider = node;
} sList->length++;
//如果current 依旧指向链表头 证明没跳走 是从0开始插入的 需要头插法
if (Current == (CircleListNode*)sList)
{
//定义一个辅助last 变量来获取尾部节点的信息
CircleListNode* last = (CircleListNode*)CircleList_Get(sList, sList->length - );
//将尾部节点的NEXT域存为当前节点(头节点)
last->next = Current->next;
}
return ;
} //获取POS位置节点的信息
CircleListNode* CircleList_Get(CircleList* list, int pos)
{ tagCircleList* sList = (tagCircleList*)list;
CircleListNode* ret = NULL;
int i = ;
if (list == NULL || pos < )
{
return NULL;
}
CircleListNode* Current = (CircleListNode*)sList;
for(i = ; i < pos; i++)
{
Current = Current->next;
} ret = Current->next;
return ret;
} //删除POS位置的节点
CircleListNode* CircleList_Delete(CircleList* list, int pos)
{
tagCircleList* sList = (tagCircleList*)list;
CircleListNode* ret = NULL; if ((sList != NULL) && (pos >=) && (sList->length > ))
{
//将Current指向表头
CircleListNode* Current = (CircleListNode*)(&(sList->header));
//辅助节点last 进行头节点的删除使用 存取最后一个元素
CircleListNode* last = NULL; for(int i = ; i < pos; i++)
{
Current = Current->next;
}
//删除头结点
if ( Current == (CircleListNode*)sList)
{
last = (CircleListNode*)CircleList_Get(sList, sList->length - );
}
//要删除的元素
ret = Current->next;
Current->next = ret->next;
sList->length--; //判断链表非空
if( last != NULL)
{
//sList->header.next = ret->next;
Current->next = ret->next;
last->next = ret->next;
}
//若删除的元素为游标所指的元素
if(sList->slider = ret)
{
sList->slider = ret->next;
}
//若删除元素后 链表长度为0 做处理
if (sList->length == )
{
sList->header.next = NULL;
sList->slider = NULL;
}
}
return ret;
} ////与游标相关的函数
//删除游标所指的位置节点
CircleListNode* CircleList_DeleteNode(CircleList* list, CircleListNode* node)
{
tagCircleList* sList = (tagCircleList*)list;
CircleListNode* ret = NULL;
int i = ; if (sList != NULL)
{
CircleListNode* Current = (CircleListNode*)sList;
//循环查找node 在链表中的位置
for (i = ; i < sList->length; i++)
{
if (Current->next == node)
{
ret = Current->next;
break;
} Current = Current->next;
}
//找到了 使用CircleList_Delete 删除
if(ret != NULL)
{
CircleList_Delete(list, i);
} } return ret;
} //重置游标位置
CircleListNode* CircleList_Reset(CircleList* list)
{
tagCircleList* sList = (tagCircleList*)list;
CircleListNode* ret = NULL;
//如果不为空
if (sList != NULL)
{
sList->slider = sList->header.next;
ret = sList->slider;
} return ret;
} //当前游标位置
CircleListNode* CircleList_Current(CircleList* list)
{
tagCircleList* sList = (tagCircleList*)list;
CircleListNode* ret = NULL;
//如果不为空
if (sList != NULL)
{
ret = sList->slider;
} return ret;
} //把游标位置返回,游标下移
CircleListNode* CircleList_Next(CircleList* list)
{
tagCircleList* sList = (tagCircleList*)list;
CircleListNode* ret = NULL;
//如果不为空
if((sList != NULL) && (sList->slider != NULL))
{
ret = sList->slider;
sList->slider = ret->next;
} return ret;
}
测试函数:
#include "circleList.h"
#include <iostream> using namespace std; typedef struct _Temp_Test
{
CircleListNode node;
int temp;
char temp2;
}TempTast; int main()
{
CircleList* circlelist = NULL; circlelist = CircleList_Create();
//异常处理
if (circlelist == NULL)
{
cout << "Create Err " << endl;
return -;
} TempTast t1, t2, t3, t4, t5;
t1.temp = ;
t2.temp = ;
t3.temp = ;
t4.temp = ;
t5.temp = ;
//插入元素
CircleList_Insert(circlelist, (CircleListNode*)(&t1), );
CircleList_Insert(circlelist, (CircleListNode*)(&t2), );
CircleList_Insert(circlelist, (CircleListNode*)(&t3), );
CircleList_Insert(circlelist, (CircleListNode*)(&t4), );
CircleList_Insert(circlelist, (CircleListNode*)(&t5), );
//测试功能
cout << "Length: " << CircleList_Length(circlelist) << endl;
//遍历两次
cout << "遍历两次:" << endl;
for(int i = ; i < *CircleList_Length(circlelist); i++)
{
cout <<"Node:" << ((TempTast*)CircleList_Get(circlelist, i))->temp << endl;
}
cout << endl;
//删除第一个节点
cout <<"Node:" << ((TempTast*)CircleList_Delete(circlelist, ))->temp << endl;
//清空
CircleList_Clear(circlelist);
cout << "After Clear Length: " << CircleList_Length(circlelist) << endl; //插入元素
CircleList_Insert(circlelist, (CircleListNode*)(&t1), );
CircleList_Insert(circlelist, (CircleListNode*)(&t2), );
CircleList_Insert(circlelist, (CircleListNode*)(&t3), );
CircleList_Insert(circlelist, (CircleListNode*)(&t4), );
CircleList_Insert(circlelist, (CircleListNode*)(&t5), );
//删除指定元素
cout << "Delete Node :" << ((TempTast*)CircleList_DeleteNode(circlelist, (CircleListNode*)(&t1)))->temp << endl;
//显示游标当前位置
cout << "Silder Now :" << ((TempTast*)CircleList_Current(circlelist))->temp << endl;
//移动后
CircleList_Next(circlelist);
cout << "Silder After Next :" << ((TempTast*)CircleList_Current(circlelist))->temp << endl;
//重置后
CircleList_Reset(circlelist);
cout << "Silder After Reset :" << ((TempTast*)CircleList_Current(circlelist))->temp << endl;
cout << endl;
//销毁
CircleList_Destroy(circlelist);
cout << "circle has been Destroied" << endl;
system("pause");
return ;
}
循环链表的C风格实现(单向)的更多相关文章
- python中的单向循环链表实现
引子 所谓单向循环链表,不过是在单向链表的基础上,如响尾蛇般将其首尾相连,也因此有诸多类似之处与务必留心之点.尤其是可能涉及到头尾节点的操作,不可疏忽. 对于诸多操所必须的遍历,这时的条件是什么?又应 ...
- 复习下C 链表操作(单向循环链表、查找循环节点)
循环链表 稍复杂点. 肯能会有0 或 6 字型的单向循环链表. 接下来创建 单向循环链表 并 查找单向循环链表中的循环节点. 这里已6字型单向循环链表为例. //创建 循环链表 Student * ...
- 03-java实现循环链表
03java实现循环链表 本人git https://github.com/bigeyes-debug/Algorithm 一丶单向循环链表 就是为尾节点指向头结点 二丶单向循环链表的接口设计 比较单 ...
- Java集合源码分析(三)LinkedList
LinkedList简介 LinkedList是基于双向循环链表(从源码中可以很容易看出)实现的,除了可以当做链表来操作外,它还可以当做栈.队列和双端队列来使用. LinkedList同样是非线程安全 ...
- 数据结构Java实现04----循环链表、仿真链表
单向循环链表 双向循环链表 仿真链表 一.单向循环链表: 1.概念: 单向循环链表是单链表的另一种形式,其结构特点是链表中最后一个结点的指针不再是结束标记,而是指向整个链表的第一个结点,从而使单链表形 ...
- 基本数据结构:链表(list)
copy from:http://www.cppblog.com/cxiaojia/archive/2012/07/31/185760.html 基本数据结构:链表(list) 谈到链表之前,先说一下 ...
- 用Python实现的数据结构与算法:链表
一.概述 链表(linked list)是一组数据项的集合,其中每个数据项都是一个节点的一部分,每个节点还包含指向下一个节点的链接(参考 <算法:C语言实现>). 根据结构的不同,链表可以 ...
- Python实现的数据结构与算法之链表详解
一.概述 链表(linked list)是一组数据项的集合,其中每个数据项都是一个节点的一部分,每个节点还包含指向下一个节点的链接.根据结构的不同,链表可以分为单向链表.单向循环链表.双向链表.双向循 ...
- 基于visual Studio2013解决算法导论之021单向循环链表
题目 单向循环链表的操作 解决代码及点评 #include <stdio.h> #include <stdlib.h> #include <time.h> ...
随机推荐
- layer窗口抖动
详细学习网址 http://www.layui.com/doc/modules/layer.html#use ..................................... //使用方法 ...
- JAVA Debug调试技术
System.out.println(e),这个方法打印出异常,并且输出在哪里出现的异常,不过它和另外一个e.printStackTrace()方法不同.后者也是打印出异常,但是它还将显示出更深的调用 ...
- 541 Reverse String II 反转字符串 II
给定一个字符串和一个整数 k,你需要对从字符串开头算起的每个 2k 个字符的前k个字符进行反转.如果剩余少于 k 个字符,则将剩余的所有全部反转.如果有小于 2k 但大于或等于 k 个字符,则反转前 ...
- [已读]ppk谈javascript
读的第一本javascript方面的书籍,印象也比较深.ppk对浏览器兼容很有研究~~可以看看他的www.quirksmode.org
- Jquery测试纠错笔记
一. 解析: 获取元素范围大小顺序依次为: $(#one).siblings("div")>$("#one~div")>$("#one + ...
- 编写可执行程序,其它程序调用,并返回数据,C#
有时候在创建临时文件或文件夹,使用完成后,释放失败,删除提示占用,又不能结束主程序,就可以通过别的方法来解决 比如,另外创建一个程序,单独执行任务,完成后结束程序,并返回执行结果,上述问题就能解决. ...
- 编译运行第一个Java程序——通过示例学习Java编程3
作者:CHAITANYA SINGH 来源:https://www.koofun.com//pro/kfpostsdetail?kfpostsid=13 在本教程中,我们将了解如何编写.编译和运行Ja ...
- 浅谈Hibernate中的三种数据状态
Hibernate中的三种数据状态:临时.持久.游离 1.临时态(瞬时态) 不存在于session中,也不存在于数据库中的数据,被称为临时态. 数据库中没有数据与之对应,超过作用域会被JVM垃圾回收器 ...
- bootstrap 滚动监听 标签页 和 工具提示
标签 <div class="container"> <h4>Tabs</h4> <ul id="myTab ...
- TCP简单程序
服务器段: package com.dcz.socket; import java.io.IOException; import java.io.OutputStream; import java.n ...