Reputation: 6756
Why the first output is including the first element (is seems to me like good behavior, because it starts with 0
index (that is that first element) and then increment with len(a)-1
(last element)).
Problem is that the second example (if it always starts with zero index and then increment) should be something like [1, 5, 4, 3, 2]
, or?
Output 1: [1, 5]
Output 2: [5, 4, 3, 2, 1]
a = [1, 2, 3, 4, 5]
print(a[::len(a)-1])
print(a[::-1])
Upvotes: 0
Views: 129
Reputation: 35069
When you provide a negative step
, the defaults for start and stop are (roughly) switched: it will start at the end of the list, and stop at the beginning. I say 'roughly' because, as you've seen, it is adjusted so that a[::-1]
still includes all of the elements of a
- meaning, it is actually equivalent to a[-1:-len(a):-1]
. The reason for this is likely related to how awkward that syntax is, compared to how useful reversing a sequence is compared to it meaning a[0:-1:-1]
, which is empty.
This is true of all builtins that support this syntax (lists, tuples and strings), but not necessarily true of any types from 3rd party modules that support it (it is up to the individual classes what slicing means for them).
Upvotes: 0
Reputation: 3145
Here is how python list slicing works:
a[start:end] # items start through end-1
There is also the step value, which can be used with any of the above:
a[start:end:step] # start through not past end, by step
The other feature is that start or end may be a negative number, which means it counts from the end of the array instead of the beginning. So:
a[-1] # last item in the array
a[-2:] # last two items in the array
a[:-2] # everything except the last two items
So, in your case,
a[::len(a)-1]
slices the array from start to end with step of len(a)-1 = 4
i.e. [1, 5] (skips the three items and retains the fourth one)
a[::-1]
inverts the array.
Upvotes: 2
Reputation: 11116
what you have is called extended slices
whatever you mention after ::
is the step value you wan to add to the 0
index element
so
>>> print(a[::len(a)-1])
[1, 5]
is basically
>>> print(a[::4)
[1, 5]
get the 0
th element and add 4 to the index and get me the next element.
Similar behaviour for negative numbers.
>>> print(a[::-1)
[5, 4, 3, 2, 1]
add -1
to the index ( or subtract 1 from the index ) which makes it 0-1
or 5
(the last element in the array).
Upvotes: 2
Reputation: 239473
The last parameter in a slice is the step value. It starts from 0, if the step is positive, -1 if the step is negative. Relevant piece of code from sliceobject.c
,
defstart = *step < 0 ? length-1 : 0;
So, when you say
a[::-1]
and as the step is negative, it just starts from the last element. It keeps on incrementing the index by -1 and the generated list is returned. So, it basically reverses the list.
But, when you say
a[::len(a)-1]
the step value is 4. Since the step is positive, it starts from the first element, which is 1
and increments the index by 4 and picks the element at index 4 (initial index (0) + 4 = 4), which is 5. That is why [1, 5]
is returned.
Upvotes: 4