实现一个函数insert,该函数接受一个Link、一个值和一个索引,并将值插入到给定索引处的Link。您可以假设链表已经至少有一个元素。不返回任何东西——insert会改变链表。
题目给的Link类的代码为
class Link:
empty = ()
#self.first是节点的值,self.rest是下一个节点的地址
def __init__(self, first, rest=empty):
assert rest is Link.empty or isinstance(rest, Link)
self.first = first
self.rest = rest
def __repr__(self):
if self.rest is not Link.empty:
rest_repr = ', ' + repr(self.rest)
else:
rest_repr = ''
return 'Link(' + repr(self.first) + rest_repr + ')'
def __str__(self):
string = '<'
while self.rest is not Link.empty:
string += str(self.first) + ' '
self = self.rest
return string + str(self.first) + '>'
首先先来说一下根据索引在列表中插入元素的思路,我这里想的是通过循环,让一个指向链表节点的指针从链表的表头一直往后移动,然后自增量加1,当自增量等于索引的时候,插入节点,思路不是很难,重点在于插入节点后链表的地址不改变,这个问题会在索引为0也就是需要在链表表头前插入节点时出现冲突,因为插入后表头的地址就变成了插入的那个节点的地址。
为了解决这个问题,即当索引值为0的时候,我想的是通过把链表copy一份,然后将插入元素的值赋值给表头的值,然后刚才copy的链表赋值给表头的rest,这样就可以实现把节点插入表头前但又不改变链表的地址。
上代码
def insert(link, value, index):
if index == 0:
pos=Link(link.first,link.rest)#pos就是copy后的新链表
link.first=value
link.rest=pos
else:
i=0
pos=link #这里pos是指向链表的指针,根据循环沿着链表从表头移动
while i!=index:
pos = link
link=link.rest
i+=1
'''
当循环终止时,pos指向索引的前一个节点,link指向索引的后一个节点,这时创建
新节点来插入
'''
new_code=Link(value)
pos.rest=new_code
new_code.rest=link
我们来看一下运行结果
link = Link(1, Link(2, Link(3)))
print(link)
other_link = link
insert(link, 9001, 0)
print(link)
print(link is other_link)