`var[:] = []` 与 `var = []` 有何不同? [复制]

Posted

技术标签:

【中文标题】`var[:] = []` 与 `var = []` 有何不同? [复制]【英文标题】:How is `var[:] = []` different from `var = []`? [duplicate] 【发布时间】:2020-03-02 21:36:15 【问题描述】:

我通常理解切片在赋值运算符左右的行为方式。

但是,我在 Python (3.8.0) 手册中看到了这一点,并试图弄清楚我缺少什么。

通过将所有元素替换为空列表来清除列表

字母[:] = []

这和letters = [] 有什么不同?

(搜索[:] 并不容易,因为*** 认为您正在寻找标签。所以,如果已经有答案,我找不到它。)

我看到一些相当不相关的答案。因此,希望清楚起见,问题不在于 [:] 切片的含义,而在于将 empty 列表分配给一个。

【问题讨论】:

***.com/questions/39241529/… 所以,我想这只是内部内存使用的问题(重用相同的内存而不是创建新列表)。可感知的代码行为没有区别,对吗? @tonypdmtr:如果某个其他变量也指向letters 指向的列表,则存在明显差异。如果你只使用letters =,那么其他变量不会受到影响,但如果你使用letters[:] =,那么通过其他变量可见的值会被修改! @JoachimSauer 好的,谢谢,这确实很重要。 这种差异最常见的地方是letters 是一个函数参数。然后letters[:] = [] 将更改传递给函数的参数,但letters = [] 不会。 【参考方案1】:

这段代码演示了发生了什么:

original = ['a','b','c']

letters = original

print('Same List')
print(original)
print(letters)

letters = []

print('Different lists')
print(original)
print(letters)

letters = original

letters[:] = []

print('Same list, but empty')
print(original)
print(letters)

输出:

Same List
['a', 'b', 'c']
['a', 'b', 'c']
Different lists
['a', 'b', 'c']
[]
Same list, but empty
[]
[]

代码的第一部分:letters = original 表示两个变量引用同一个列表。

第二部分:letters = [] 表明这两个变量现在引用了不同的列表。

第三部分:letters = original; letters[:] = [] 以两个变量再次引用同一个列表开始,但随后列表本身被修改(使用[:])并且两个变量仍然引用相同但现在修改的列表。

【讨论】:

【参考方案2】:

分配var = [] 绑定名称var 到新创建的列表。名称var 之前可能已绑定或未绑定到任何其他列表,如果已绑定,则该列表将保持不变。

另一方面,var[:] = [] 期望 var 已经绑定到一个列表,并且该列表已就地更改。

这就是这两种情况下的行为不同的原因:

var1 = [1, 2, 3]
var2 = var1
var1 = []
print(var1, var2)  # prints [] [1, 2, 3]

var1 = [1, 2, 3]
var2 = var1
var1[:] = []
print(var1, var2)  # prints [] []

【讨论】:

【参考方案3】:

var = [] 是对名称 var 的赋值。它用[] 替换了var 所指的内容(如果有的话)。

var[:] = [] 是变相的方法调用:var.__setitem__(slice(), [])。它用[] 中的元素替换切片引用的元素(在本例中为所有元素),有效地清空列表而不完全替换它。

顺便说一句,您可以使用var.clear() 来完成同样的事情;更一般地,切片分配允许您将一个范围的值替换为另一个可能更长或更短的值范围。

【讨论】:

它是把列表复制到一个新的列表中还是已经到位? 就地。看到这一点的最好方法可能是使用var = [1,2,3]; b = var; var[:] = []; assert b == [] 之类的东西。通过var 所做的更改也可以通过b 看到。

以上是关于`var[:] = []` 与 `var = []` 有何不同? [复制]的主要内容,如果未能解决你的问题,请参考以下文章

var 与具体类型的用法[重复]

浅析constlet与var

var与变量提升

Var与Dynamic的区别

let 与 var

尝试将 AngularJS var 与 Laravel Blade var 连接起来