繁体   English   中英

如何在不修改 Python 中的原始列表的情况下反转列表

[英]How to reverse a list without modifying the original list in Python

我正在尝试通过以下方式使用 reverse() 方法:

>>> L=[1,2,3]
>>> R=L
>>> L.reverse()
>>> L
[3, 2, 1]
>>> R
[3, 2, 1]

为什么它也会反转 R? 如何保留原始列表并创建反向列表?

谢谢!

你需要复制一份你的清单

L=[1,2,3]
# R=L
R = L[:]
L.reverse()

或更直接(使用切片符号反转):

R = L[::-1]

如果你只是写R = L那么R只是同一个列表L上的一个新引用。

如果您还需要复制列表中的元素,请使用copy.deepcopy R = L[:]只产生一个浅拷贝(这在你的情况下很好,列表中只有int s)。

为避免反转R ,您需要一份L的副本

要复制,请更改

R=L    <---- this is not copying L in to R

R= L[:]    <---- this will create a copy of L in to R
>>> L=[1,2,3]
>>> R=list(reversed(L))
>>> R
[3, 2, 1]
>>> L
[1, 2, 3]

这会做

R = L[:]

阅读有关复制和深度复制的内容以了解发生这种情况的原因。 简而言之,这是因为当您执行R = L ,两者都指向内存中的“相同”列表,因此反转一个将反转另一个。

或者,您可以使用deepcopy

操作

R=L

意味着变量 R 存储 L 正在存储的任何内容,即 R 对 L 所引用的任何值的引用。 现在,当您反转 L 时,这意味着 L 所引用的列表已反转。由于 R 也引用了相同的地址,因此您将看到 R 已反转。

您已经被 Python 分配引用而不是副本这一事实所困扰。

Python 仅使用引用来防止不需要的副本。 它在传递函数参数时也使用引用,甚至使用默认函数参数。 它仅在您明确告诉它时才会复制,例如通过执行

L = list(R)

或者

from copy import copy
L = copy(R)

两者的区别在于list(R)总是返回一个列表,其中copy返回一个与原始类型相同的对象。 此外, copy不适用于迭代器,但list可以。

请注意,这些是“浅”副本。 如果列表包含对象,则新列表包含对相同对象的引用。 对于“深度”副本,它在模块copy具有deepcopy功能。

from copy import deepcopy
L = deepcopy(R)

但在实践中很少需要制作显式副本。 Python 提供了例如可用于遍历列表的reversed内置函数。

for l in reversed(L):
    # do stuff

它返回一个迭代器,所以它是高效的。 无需复制列表。 其他可能需要副本的情况可以由例如生成器函数处理。 复制的有效情况可能是将数据传递到线程边界之外。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM