单向循环链表的增、删、查、改

具体代码如下:

class Node(object):"""链表单节点实现"""def __init__(self, item):self.item = item  # 元素域self.next = None  # 链接域class CycleleLink:"""单向循环链表"""def __init__(self, node=None):self.__head = node# head为指向一个链表头结点的p变量,接收一个参数node,node就是一个结点(第一个结点),当然也可以不传参数,# 当做一个空链表# head设置成私有属性,防止外部访问,如果head被外部访问并改动,则head之前指向的链表就丢失找不到了def is_empty(self):"""判断链表是否为空:return 如果链表为空, 返回真"""return self.__head is Nonedef length(self):""":return: 链表长度 cur 游标count 结点计数"""if self.is_empty():return 0else:cur = self.__head  # 设置游标指向第一个结点count = 1  # 计数初始值为:1while cur.next != self.__head:  # 如果游标指向的结点的next为head则表示该结点为链表的最后一个元素count += 1  # 每次加一cur = cur.next  # 如果cur不为空则让游标指向下一个结点return count  # 最后返回链表长度def travel(self):"""遍历链表:return:打印链表所有元素"""if self.is_empty():return  # 如果链表是空的就直接返回 cur = self.__headwhile cur.next != self.__head:print(cur.item, end=" ")cur = cur.nextprint(cur.item)# 最后一个元素的next为head,不进入循环也就不会打印,所以在此处补充打印def add(self, item):"""在链表头部添加结点:param item: 结点元素:return: """node = Node(item)  # 创建一个结点对象# 链表为空时特殊处理if self.is_empty():self.__head = nodenode.next = node  # 即使只有一个结点时也要遵循循环链表规则,尾结点指头# 该链表的尾部的next指向head所以在头部# 所以要改变head要先找到最后一个元素cur = self.__headwhile cur.next != self.__head:cur = cur.next# 此while循环结束后cur就指向了最后一个结点了node.next = self.__head  # 让新结点的next指向原始的第一个结点self.__head = node  # 让头指针指向新加入的结点cur.next = node  # 让最后一个结点的next指向新的头结点def append(self, item):"""在链表的尾部追加结点:param item: :return: """node = Node(item)#  如果链表为空则需要特殊处理if self.is_empty():self.__head = nodenode.next = node  # 尾元素指向头部不在赘述else:cur = self.__headwhile cur.next != self.__head:cur = cur.next# while循环结束后cur指向最后一个结点cur.next = node  # 尾部追加结点node.next = self.__head  # 新尾结点指头def insert(self, pos, item):"""在指定位置插入元素:param item: :return: """# TODO 此方法代码涉及头尾的都已封装好了,其余代码也不需要更改(与单链表相同)if pos <= 0:  # 如果要插入的位置小于等于0,则相当于在头部加入结点self.add(item)  # 直接调用已经写好的方法elif pos >= self.length():  # 如果要插入的位置大于等于链表的长度,则相当于在链表的尾部追加元素self.append(item)  # 直接调用写好的方法else:  # 如果插入位置在链表中间则进行一下操作cur = self.__head  # 游标指向第一个结点count = 0  # 计数制0while count < (pos - 1):  # (pos - 1) cur需要停留在pos位置的前一个结点的位置cur = cur.nextcount += 1# 当退出循环的时候cur指向pos的前一个位置node = Node(item)  # 创建新结点node.next = cur.next  # 将新结点指向cur的下一个结点cur.next = node  # 将cur指向新结点def remove(self, item):"""删除结点"""# TODO 此方法重点特殊处理if self.is_empty():  # 如果链表为空直接返回returncur = self.__headpre = None  # 设置前后两个游标,cur,prewhile cur.next != self.__head:  # 如果cur不为空则进入循环if cur.item == item:  # 找到了要删除的元素if cur == self.__head:  # 如果找到的元素在头结点上rea = self.__headwhile rea.next != self.__head:rea = rea.next# 此while循环结束时rea指向尾结点self.__head = cur.next  # 让头结点指向下一个结点,丢弃上个结点rea.next = self.__headelse:  # 找到的结点不在头结点上,# 让在目标结点的前一个结点的next指向目标结点的后一个结点,使目标结点的引用变成0,被丢弃pre.next = cur.nextreturn  # 删除后直接结束循环else:pre = cur  # 让前一个游标向后移指向cur,让cur向后移指向cur的下一个结点cur = cur.next# 退出外层while时,cur指向尾结点,没有进入循环,也没有判断,在此处处理一下if cur.item == item:if cur.next == self.__head:  # cur指向尾结点,而cur的next指向head则表明链表只有一个结点self.__head = Noneelse:pre.next = self.__headdef search(self, item):"""查找结点是否存在:return 布尔型"""if self.is_empty():return Falsecur = self.__headwhile cur != self.__head:if cur.item == item:return True  # 如果找到了目标结点就返回truecur = cur.next# while退出时cur指向尾结点,没有进入循环,也没有判断,在此处处理一下if cur.item == item:return Truereturn False  # 如果整个循环结束也没有找到目标结点,就返回falseif __name__ == '__main__':link = CycleleLink()print(link.length())print(link.is_empty())link.add(1)link.travel()link.append(6)link.travel()link.insert(1, 3)link.travel()print(link.length())print(link.search(1))link.remove(3)link.travel()link.remove(6)link.remove(1)print(link.length())

总结: 单向循环链表操作重点注意:
1 判空
2 首尾结点特殊情况处理
3 链表只有一个结点时的next指向自己

单向循环链表的增、删、查、改、python实现,超详细讲解相关推荐

  1. 单链表的增、删、查、改、python实现,超详细讲解

    单链表的python实现 代码增.删.查.改.及超详细注释: class Node(object):"""链表单节点实现"""def __i ...

  2. java 增 删 查 改_如何对java链表进行增、删、查、改操作

    如何对java链表进行增.删.查.改操作 发布时间:2020-06-23 10:41:33 来源:亿速云 阅读:79 作者:Leah 如何对java链表进行增.删.查.改操作?针对这个问题,今天小编总 ...

  3. 双向链表的增、删、查、改、python实现,超详细讲解

    双向链表的增.删.查.改 具体代码如下: class Node(object):"""链表单节点实现"""def __init__(self ...

  4. Python爬虫超详细讲解(零基础入门,老年人都看的懂)!

    注重版权,转载请注明原作者和原文链接 作者:码农BookSea 原文链接:https://blog.csdn.net/bookssea/article/details/107309591 先看后赞,养 ...

  5. 快速排序 - python版超详细讲解

    快速排序 快速排序(英语:Quicksort),又称划分交换排序(partition-exchange sort),通过一趟排序将要排序的数据分割成独立的两部分,其中一部分的所有数据都比另外一部分的所 ...

  6. 100个python算法超详细讲解:抢30游戏

    [100个python算法超详细讲解]@谷歌学术 1.问题描述 由两个人玩"抢30"游戏,游戏规则是:第一个人先说"1"或"1,2",第 二 ...

  7. Python的零基础超详细讲解(第十三天)-Python的类与对象

    基础篇往期文章如下: Python的零基础超详细讲解(第一天)-Python简介以及下载 Python的零基础超详细讲解(第二天)-Python的基础语法1 Python的零基础超详细讲解(第三天)- ...

  8. Python的零基础超详细讲解(第十二天)-Python函数及使用

    基础篇往期文章: Python的零基础超详细讲解(第一天)-Python简介以及下载_编程简单学的博客-CSDN博客 Python的零基础超详细讲解(第二天)-Python的基础语法1_编程简单学的博 ...

  9. Python的零基础超详细讲解(第七天)-Python的数据的应用

    往期文章 Python的零基础超详细讲解(第一天)-Python简介以及下载_编程简单学的博客-CSDN博客 Python的零基础超详细讲解(第二天)-Python的基础语法1_编程简单学的博客-CS ...

最新文章

  1. 加拿大留学商科好还是计算机科学好,去加拿大读商科专业就是要选择这些才最好!...
  2. zookeeper for mac安装
  3. Exchange 2016 批量添加X500地址,解决迁移后退信的问题
  4. PyTorch系列入门到精通——BN、LN、IN and GN
  5. matlab meshgrid
  6. python--requests库 安装及简单使用
  7. 学习3 二维游戏动画合成(侠客行)
  8. Nokia手机S40平台手机开发环境的搭建的过程
  9. ArcFace: AdditiveAngularMarginLossforDeepFaceRecognition
  10. TN3399开发板折腾记录
  11. python三行代码抠图_Python用5行代码如何实现批量抠图 Python用5行代码实现批量抠图方法...
  12. 产业新基建,撬动数字经济发展新机遇
  13. 屏幕尺寸大全和UI设计规范
  14. MatchNet: Unifying Feature and Metric Learning for Patch-Based Matching
  15. linux分区写保护,mtd分区写保护关闭
  16. 关于求1~n中与m互质的数的个数(容器原理+数论分解质因子)
  17. linux天翼校园认证失败,天翼校园账号状态异常?这份超详细图文教程帮你解决问题!...
  18. 1. 辐射发射--RE
  19. 警惕!黑客原来是这样远程攻击劫持安卓手机
  20. windebug分析高cpu问题

热门文章

  1. javascript--DOM概念
  2. 软考信息安全必备考点
  3. java基础----数据类型转化
  4. Linux运维系统工程师系列---11
  5. 部署SCVMM2012 SP1 集群(1)---部署AD
  6. SEO(search engine optimization)搜索引擎优化
  7. mysql replication
  8. 企业文件服务器(samba)配置案例一
  9. Linux模拟超级终端minicom(二)
  10. 快速搭建 SpringCloud 微服务开发环境的脚手架