teaching myself algorithms。我需要交换清单上的两个项目。python让一切变得简单:

def swap(A, i, j):
    A[i], A[j] = A[j], A[i]

这是一种享受:
>>> A = list(range(5))
>>> A
[0, 1, 2, 3, 4]
>>> swap(A, 0, 1)
>>> A
[1, 0, 2, 3, 4]

注意,该函数对退化情况具有弹性。正如您所期望的,它只是保持列表不变:
>>> A = list(range(5))
>>> swap(A, 0, 0)
>>> A
[0, 1, 2, 3, 4]

后来我想在一个列表中排列三个项目。我编写了一个函数,将它们排列成3个循环:
def cycle(A, i, j, k):
    A[i], A[j], A[k] = A[j], A[k], A[i]

这很有效:
>>> A = list("tap")
>>> A
['t', 'a', 'p']
>>> cycle(A, 0, 1, 2)
>>> A
['a', 'p', 't']

然而,我(最终)发现它在退化的情况下是错误的。我假设一个退化的3周期是一个交换。因此,当:
>>> A = list(range(5))
>>> cycle(A, 0, 0, 1)
>>> A
[1, 0, 2, 3, 4]

但是当其他事情发生时:
>>> A = list(range(5))
>>> sum(A)
10
>>> cycle(A, 1, 0, 1)
>>> A
[1, 1, 2, 3, 4]
>>> sum(A)
11

发生什么事?i = j在任何排列下都应该是不变的!为什么这个案例的退化不同?
我怎样才能实现我想要的?这是一个三周期函数,如果只有两个指数不同,则退化为交换。

最佳答案

cycle正按照您的要求执行:将右手值指定给左手值。

def cycle(A, i, j, k):
    A[i], A[j], A[k] = A[j], A[k], A[i]

在功能上等同于
def cycle(A, i, j, k):
    new_values = A[j], A[k], A[i]
    A[i], A[j], A[k] = new_values

所以当你这样做的时候,你所说的就是你想要的
A[1] = previous_A[0]
A[0] = previous_A[1]
A[1] = previous_A[1]

如果您希望循环按顺序工作,那么您必须按顺序编写它,否则Python将计算右手边的值,然后将其扩展到左手边的参数。

关于python - 在多次分配的退化情况下会发生什么?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/34882417/

10-13 00:02