传递给函数时链接列表的确如何表现?
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了传递给函数时链接列表的确如何表现?相关的知识,希望对你有一定的参考价值。
这是我的Node类:
class Node:
def __init__(self, value):
self.value = value
self.next = None
def __repr__(self):
if self.next == None:
return 'Node({})'.format(repr(self.value))
else:
return 'Node({}, {})'.format(
repr(self.value), repr(self.next))
这是我的方法m:
def m(lnk):
while lnk and lnk.next:
lnk.next = lnk.next.next
lnk = lnk.next
print(lnk)
然后我运行以下代码:
lnk = Node(1)
lnk.next = Node(2)
lnk.next.next = Node(3)
m(lnk)
print(lnk)
第一个输出是Node(3),第二个输出是Node(1,Node(3))。我理解第一个输出,但它是我没有真正得到的第二个输出。为什么Node(1)仍在那里?我认为lnk将作为参考传入,因此会改变并具有与我的函数中相同的值。但是,这没有发生,我不明白为什么。
你现在的问题是你的m函数没有按照预期的那样做。通过删除行lnk.next = lnk.next.next
来更改它:
def m(lnk):
while lnk and lnk.next:
lnk = lnk.next
print(lnk)
然后,您将获得以下结果:
>>> m(lnk)
Node(3)
>>> print(lnk)
Node(1, Node(2, Node(3)))
那么,做什么呢?
__repr__
说如果你是列表的最后一部分,返回“Node(#)”,其中#是值。如果您不是列表的最后一部分,请返回您下方的节点列表。
修改后的m
函数现在只需打印列表中的最后一个节点。
详细了解您当前的设置以及您的m
功能的作用:
当前:lnk = {'value':1,'next':{'value':2,'next':{'value':3,'next':None}}}
你的循环通过m
的第一次传递采用你传入的对象,称为lnk
,它定义如上,并改变它lnk = {'value':1,'next':{'value':3,'next ':None}}(因为lnk.next = lnk.next.next)。在循环中的第二次传递中,lnk
变量已更改。它不再指向同一个对象;它指向对象{'value':3,'next':None},循环停止,因为'next'是None。
请注意,这修改了您的链接列表,我不认为这是意图。
Evan指出你的参考是一个很好的参考。在阅读有关内容时,您会看到函数内的变量名是本地的。它首先引用您创建的Node(1)对象,但是当您将其分配给其他对象时,它不再引用该对象。但是,它不是通过值传递的,因为您在该对象内部进行的更改(例如设置lnk.next.next)仍然存在。
创建初始链接列表时,需要使用.next.next
语法来避免为每个节点创建临时变量。你也可以像这样构建你的列表:
node1 = Node(1)
node2 = Node(2)
node3 = Node(3)
node1.next = node2
node2.next = node3
linked_list = node1
现在,如果要更新lnk
以指向列表的尾部,则需要返回本地变量。 m
及其用法应该是这样的:
def m(node):
while node and node.next:
node = node.next
return node
tail = m(lnk)
请注意,我将m
的参数重命名为node
。这应该可以帮助您避免混淆lnk
的设置或修改位置。如果您继续修改列表,请意识到您的结果仍然相同。即使它被命名为node
,行node.next = node.next.next
仍然会在更高的范围内修改名为lnk
的变量。
在风格说明中,我强烈建议永远不要命名功能m
。给它一个名字,如get_tail
或get_leaf
,所以很清楚这个功能是做什么的。至少你的一些困惑来自于没有明确定义m应该做什么。
如果你必须修改函数内部的lnk
变量(变量本身,而不是内容),你可以使用全局变量来做,但这几乎总是一个坏主意,不应该这样做。 (因为人们习惯于变量的行为,并且改变行为会使代码更难维护。在这种情况下,大多数人都希望链接列表上的操作不具有破坏性,除非它在语义上明显是他们想要的,例如pop
。)
def m():
global lnk
while lnk and lnk.next:
lnk = lnk.next
Variables in Python are not passed by reference, but by assignment.它实际上与在C或C ++中传递指针变量相同:如果更改函数内可变对象的字段,则更改将在调用范围中可见,但如果更改变量本身的标识,它不会。
以上是关于传递给函数时链接列表的确如何表现?的主要内容,如果未能解决你的问题,请参考以下文章
OnItemClick 如何从列表视图中获取单击项目的文本值