没有返回值的递归反向列表

我编写递归函数以就地反向列表时遇到以下问题。我可以更改输入参数。

getOrDefault

输出为

def reverse_string(s):
    if len(s) <= 1:
        return
    else:
        s[0],s[-1] = s[-1],s[0]
        reverse_string(s[1:-1])


s = ['A','B','C','D','E','F']
reverse_string(s)
print(s)

在递归调用返回之后,看起来我在递归中所做的更改已回滚。我不明白为什么。有人可以帮忙吗?

hf2baobei 回答:没有返回值的递归反向列表

切片列表会创建一个新列表,因此修改切片列表不会影响原始列表。相反,您可以使函数接受偏移量作为第二个参数,以便根据列表两端的偏移量对项目进行交换:

def reverse_string(s,offset=0):
    if len(s) > offset * 2:
        s[offset],s[-offset - 1] = s[-offset - 1],s[offset]
        reverse_string(s,offset + 1)

这样:

s = ['A','B','C','D','E','F']
reverse_string(s)
print(s)

输出:

['F','A']
,

要了解您当前的代码如何工作,以下是使用与起作用相同的算法的版本。它只是增加了一些额外的步骤,以便您可以适当地处理在每次调用时从主列表中切出的列表:

def reverse_string(s):
    if len(s) <= 1:
        return
    else:
        s[0],s[-1] = s[-1],s[0]
        slice = s[1:-1]       # slicing a list creates a new,independent list object
        reverse_string(slice) # this call modifies the new list in place,leaving s unchanged
        s[1:-1] = slice       # so we have to assign the modified slice back to s ourselves

请注意,尽管这样做确实有效,但效率极低,因为切片和切片分配都需要在每次递归调用中复制列表的很大一部分。其他答案给出了更有效的解决方案,其中涉及始终修改同一列表,仅使用特定索引而不是始终交换s[0]s[-1]

还值得注意的是,虽然这是list对象在切片时的行为,但Python中的其他对象的行为可能有所不同。 numpy数组中的一个切片是另一个数组,但是数组是基础数据的浅“视图”。经常在原位置修改数组的某个切片 也会修改它来自数组中的数据。这可能是好事,也可能是坏事,这取决于您是否期望!

,

希望这只是递归练习,这是python内置的使用负增量反转列表的效率相当低的实现

s = ['A','F']
print(s[::-1])

有关递归,请参阅blhsing的答案。

,

由于s[::-1]是反转的建议答案,因此我们也需要说明reverse,因为这是反转切片(就地)的最快方法

s = ['A','F']
s.reverse()
print(s)
# ['F','A']
本文链接:https://www.f2er.com/3069683.html

大家都在问