Python:为什么 [0,1,2][-1:1] 不引发错误?

Python: Why doesn't [0,1,2][-1:1] raise an error?

在 Python 中,可以使用数组切片表示法来获取可迭代对象中的值的子集:

a = [0,1,2]
a[0:2]
# returns all members from the 0th to the 2nd: [0,1]

如果您尝试提取第一个值为负而第二个值为正的切片,则请求 return 是一个空列表:

a[-1:2]
# returns []

这对我来说是违反直觉的,因为 -1:2 定义的范围似乎是 0:2.[=14= 定义的范围的 超集 ]

我知道可以使用负索引从带有 Python 切片符号的数组末尾提取(例如:a[-1] 是 2),但它在第一个中似乎是负值切片位置和第二个中的正数应该引发错误或 return 值的超集 return 由同一个切片编辑,第一个位置为 0。

我很想知道空列表背后的动机 return 如果有人恰好对此有所了解,则由第一个位置为负值而第二个位置为正值的切片请求编辑正面...

负索引对于获取最后一个元素非常有用:

>>> letters = list('abcdefgh')
>>> letters[-3:]
['f', 'g', 'h']
>>> letters[-3:-1]
['f', 'g']

在这种情况下过早地引发异常将是一个巨大的错误。

您还可以混合使用负索引和正索引:

>>> letters[-5:6]
['d', 'e', 'f']

表示倒数第 5 个元素之后和第 6 个元素之前的元素。

你的情况:

>>> letters[-1:2]
[]

Returns 一个空列表,因为最后一个和第二个之间没有元素。

虽然它并不总是空的:

>>> ['a'][-1:2]
['a']
>>> ['a','b'][-1:2]
['b']

我认为这只是一个误解:负值被解释为 "counting from the end",因此 [-1:2] 不是 [0:2] 的超集。恰恰相反!因为无论 -1 是什么(实际值取决于 iterable 的长度)它总是 >= 0.

在你的例子中,你有一个长度为 3 的数组,所以 -1 被解释为 2 并且你想要获取 2 和 2 之间的项目(停止独占),所以你得到一个空列表。

假设您想要最后 10 个元素的一部分。这很容易用 a[-10:] 完成。如果这会引发错误,您可能会写一些令人不快的东西,例如 a[len(a)-10:]。更糟糕的是,如果 a 不是您之前使用的带有列表的变量,而是您现在计算的内容,您将需要创建一个新变量才能获得长度。如果你可以在最后写 [-10:],你就不需要。

显然,当这不是预期的行为时,这可能会有缺点,但在其他情况下为了简洁起见,这可能是值得的。