python中的list.append(another_list) vs list.append(another_list[:])? [复制]
Posted
技术标签:
【中文标题】python中的list.append(another_list) vs list.append(another_list[:])? [复制]【英文标题】:list.append(another_list) vs list.append(another_list[:]) in python? [duplicate] 【发布时间】:2016-03-11 02:31:55 【问题描述】:这是我必须做的一个问题:
我们将实现一个非常有用的函数,称为 group。
group 接受一个事物列表并返回一个组列表,其中每个组由列表中所有相等的连续元素组成。
例如:
group([1, 1, 1, 2, 3, 1, 1]) == [[1, 1, 1], [2], [3], [1, 1]]
group([1, 2, 1, 2, 3, 3]) == [[1], [2], [1], [2], [3, 3]]
这是我最初的解决方案:
def group(int_list):
group_list = []
current_list = []
for i in range(len(int_list)):
if int_list[i] not in current_list:
if len(current_list) != 0:
group_list.append(current_list)
del current_list[:]
current_list.append(int_list[i])
else:
current_list.append(int_list[i])
group_list.append(current_list)
return group_list
我得到的输出:
[[1, 1], [1, 1], [1, 1], [1, 1]]
在花了大约 30 分钟试图找出问题后,我将第 9 行从 group_list.append(current_list)
更改为 group_list.append(current_list[:])
,令人惊讶的是,魔法奏效了。我得到了正确的输出:
[[1, 1, 1], [2], [3], [1, 1]]
所以我想我的问题是 current_list
和 current_list[:]
有什么区别?
【问题讨论】:
修复原始代码的另一种方法是将del current_list[:]
更改为current_list = []
,这样下次你追加current_list
时它会是一个不同的列表(即不需要做一个浅拷贝)。
【参考方案1】:
current_list[:]
是current_list
的浅拷贝;例如:
在您的函数中,您在current_list
所指的事物中建立一个(当前组的)列表。完成后,将此事物添加到 group_list
,然后通过删除其所有内容 (del current_list[:]
) 来重置事物。我们必须记住,Python 中的所有内容都是引用,因此,使用您的第一个代码,group_list
包含对 same object 的多个引用(这就是您的输出看起来像 [[1, 1], [1, 1], [1, 1], [1, 1]]
的原因)。当您删除current_list
的内容并稍后添加新元素时,您也会对group_list
的每个元素执行此操作。
使用您发现的current_list[:]
语法,创建current_list
的副本并将其添加到group_list
;当您删除current_list
的内容后,此副本不会被修改。
【讨论】:
那么这是正确的做法吗?只需添加 [:] @BobbyBrown 似乎共识是,就代码风格而言,通过编写list(current_list)
创建浅拷贝比current_list[:]
更清晰。不过,这只是美学;使用切片运算符创建副本工作正常。【参考方案2】:
主要区别在于 current_list 是对列表的引用,而 current_list[:] 是包含列表元素的新数组。因此,使用第一个,当您更改 current_list 时,group_list 也会更改。反之,如果您更改 current_list,group_list 不会被修改。
【讨论】:
以上是关于python中的list.append(another_list) vs list.append(another_list[:])? [复制]的主要内容,如果未能解决你的问题,请参考以下文章
python中List append()extend()和insert()的区别