python环形单链表的约瑟夫问题详解
作者:冬日新雨 发布时间:2023-03-02 04:13:10
标签:python,环形单链表,约瑟夫
题目:
一个环形单链表,从头结点开始向后,指针每移动一个结点,就计数加1,当数到第m个节点时,就把该结点删除,然后继续从下一个节点开始从1计数,循环往复,直到环形单链表中只剩下了一个结点,返回该结点。
这个问题就是著名的约瑟夫问题。
代码:
首先给出环形单链表的数据结构:
class Node(object):
def __init__(self, value, next=0):
self.value = value
self.next = next # 指针
class RingLinkedList(object):
# 链表的数据结构
def __init__(self):
self.head = 0 # 头部
def __getitem__(self, key):
if self.is_empty():
print 'Linked list is empty.'
return
elif key < 0 or key > self.get_length():
print 'The given key is wrong.'
return
else:
return self.get_elem(key)
def __setitem__(self, key, value):
if self.is_empty():
print 'Linked list is empty.'
return
elif key < 0 or key > self.get_length():
print 'The given key is wrong.'
return
else:
return self.set_elem(key, value)
def init_list(self, data): # 按列表给出 data
self.head = Node(data[0])
p = self.head # 指针指向头结点
for i in data[1:]:
p.next = Node(i) # 确定指针指向下一个结点
p = p.next # 指针滑动向下一个位置
p.next = self.head
def get_length(self):
p, length = self.head, 0
while p != 0:
length += 1
p = p.next
if p == self.head:
break
return length
def is_empty(self):
if self.head == 0:
return True
else:
return False
def insert_node(self, index, value):
length = self.get_length()
if index < 0 or index > length:
print 'Can not insert node into the linked list.'
elif index == 0:
temp = self.head
self.head = Node(value, temp)
p = self.head
for _ in xrange(0, length):
p = p.next
print "p.value", p.value
p.next = self.head
elif index == length:
elem = self.get_elem(length-1)
elem.next = Node(value)
elem.next.next = self.head
else:
p, post = self.head, self.head
for i in xrange(index):
post = p
p = p.next
temp = p
post.next = Node(value, temp)
def delete_node(self, index):
if index < 0 or index > self.get_length()-1:
print "Wrong index number to delete any node."
elif self.is_empty():
print "No node can be deleted."
elif index == 0:
tail = self.get_elem(self.get_length()-1)
temp = self.head
self.head = temp.next
tail.next = self.head
elif index == self.get_length()-1:
p = self.head
for i in xrange(self.get_length()-2):
p = p.next
p.next = self.head
else:
p = self.head
for i in xrange(index-1):
p = p.next
p.next = p.next.next
def show_linked_list(self): # 打印链表中的所有元素
if self.is_empty():
print 'This is an empty linked list.'
else:
p, container = self.head, []
for _ in xrange(self.get_length()-1): #
container.append(p.value)
p = p.next
container.append(p.value)
print container
def clear_linked_list(self): # 将链表置空
p = self.head
for _ in xrange(0, self.get_length()-1):
post = p
p = p.next
del post
self.head = 0
def get_elem(self, index):
if self.is_empty():
print "The linked list is empty. Can not get element."
elif index < 0 or index > self.get_length()-1:
print "Wrong index number to get any element."
else:
p = self.head
for _ in xrange(index):
p = p.next
return p
def set_elem(self, index, value):
if self.is_empty():
print "The linked list is empty. Can not set element."
elif index < 0 or index > self.get_length()-1:
print "Wrong index number to set element."
else:
p = self.head
for _ in xrange(index):
p = p.next
p.value = value
def get_index(self, value):
p = self.head
for i in xrange(self.get_length()):
if p.value == value:
return i
else:
p = p.next
return -1
然后给出约瑟夫算法:
def josephus_kill_1(head, m):
'''
环形单链表,使用 RingLinkedList 数据结构,约瑟夫问题。
:param head:给定一个环形单链表的头结点,和第m个节点被杀死
:return:返回最终剩下的那个结点
本方法比较笨拙,就是按照规定的路子进行寻找,时间复杂度为o(m*len(ringlinkedlist))
'''
if head == 0:
print "This is an empty ring linked list."
return head
if m < 2:
print "Wrong m number to play this game."
return head
p = head
while p.next != p:
for _ in xrange(0, m-1):
post = p
p = p.next
#print post.next.value
post.next = post.next.next
p = post.next
return p
分析:
我采用了最原始的方法来解决这个问题,时间复杂度为o(m*len(ringlinkedlist))。
但是实际上,如果确定了链表的长度以及要删除的步长,那么最终剩余的结点一定是固定的,所以这就是一个固定的函数,我们只需要根剧M和N确定索引就可以了,这个函数涉及到了数论,具体我就不细写了。
来源:https://blog.csdn.net/dongrixinyu/article/details/78717547


猜你喜欢
- 环境 MySQL 5.1 + 命令行工具 问题 MySQL表字段设置默认值 解决 --SQL: CREATE TABLE test( i_a
- 本文实例讲述了PHP学习记录之面向对象(Object-oriented programming,OOP)基础。分享给大家供大家参考,具体如下
- jQuery由美国人John Resig创建,至今已吸引了来自世界各地的众多javascript高手加入其team,包括来自德国的J&
- 1、Introduction之前写过2篇文章,分别是:Mysql主从同步的原理 Myql主从同步实战 基于此,我们再实
- 现在来看小程序还没有使用pc端的那种分页格式,现在微信小程序上分页一般使用触底加载来实现分页的,下面就来分享一个触底加载的实现方式。1.首先
- MySQL GUI Tools是一套图形化桌面应用工具套装,可以用来管理MySQL服务器。该套装工具包含三个工具:MySQL Query B
- 添加事件禁止选择、拖拽、右键(简单的禁止用户保存图片,但无法阻止用户打开控制台查看,或是直接抓包)将之转换为 canvas(让浏览器认为不是
- 目录时间戳相减装饰器timeit模块重复调用 timeit()cProfile性能分析工具时间戳相减在代码执行前后各记录一个时间点,两个时间
- int(10)int(20)分别代表什么意思储备知识在设计数据库表的时候,经常需要设计一个id字段,它的类型一般都是整型int,经常会遇到i
- 近来看论坛上经常有人提问关于如何无刷新,自动更新数据.传统上,我们浏览网页,如果加入最新的数据.只能是等我们重新向服务器端请求时才能显示出来
- 1、从外部文档中粘贴时,如果不想要其格式,只要文字,可以使用“Edit->paste as text”命令,而不要直接Ctrl+V。2
- T-SQL中用来编写流程控制模块的语句有:BEGIN...AND语句、IF...ELSE语句、CASE语句、WHILE语句、GOTO语句、B
- 如下所示:>>> item={} ; items=[] #先声明一个字典和一个列表,字典用来添加到列表里面&g
- 前言:在Python中,如果我们想要在遍历一组数据的过程中,对这组数据进行修改,通常会出现许多问题,例如对列表进行上述操作时, 会忽略部分数
- 使用mysql主从复制的好处有:1、采用主从服务器这种架构,稳定性得以提升。如果主服务器发生故障,我们可以使用从服务器来提供服务。2、在主从
- PHP7.0正式版也出来了,今天编译安装了一下,写下安装步骤,我是在centos6.6 环境中编译的,下面是详细的安装步骤环境依赖yum i
- 觉得废话多的话,可以直接看代码作用防止有人不停的刷接口,对接口作限制比如说,登录接口,按道理说,应该只有app会请求这个接口但是,如果有人抓
- 本文实例为大家分享了python给心爱的人每天发天气预报的具体代码,供大家参考,具体内容如下下面的代码实现了用了之前获取天气的代码,然后用i
- 1.散点图代码# This import registers the 3D projection, but is otherwise unu
- 本文实例讲述了php+mysqli使用面向对象方式更新数据库的方法,分享给大家供大家参考。具体实现方法如下:<?php//第一步:创建