[Python-ideas] Where did we go wrong with negative stride?

Tim Peters tim.peters at gmail.com
Mon Oct 28 21:56:59 CET 2013


[Tim]
>> As Guido noted, under the proposal we have:
>>
>>     s[i:j:k] == s[i:j][::k]
>>
>> That should (finally?) make it crystal clear that applying the stride
>> has nothing directly to do with the indices of the selected elements
>> in the original sequence (`s`).

[Bruce Leban]
> It's definitely not "finally clear" as it's a change in semantics.

Of course it is.

> What about negative strides other than -1?

All strides start the same way, by (conceptually) selecting s[i:j]
first.  Then the stride is applied to that contiguous slice, starting
with the first element and taking every abs(k) element thereafter.
Finally, if k is negative, that sequence is reversed.  k=1, k=-1, k=2,
k=-2, ..., all the same.

> Which of these is expected?
>
> (A) '012345678'[::-2] == '86420'
>     '0123456789'[::-2] == '97531'
> or:
>
> (B) '012345678'[::-2] == '86420'
>     '0123456789'[::-2] == '86420'

B.


> If (A) I can get the (B) result by writing [::2][::-1] but if (B), I'm
> forced to write:
>
> s[0 if len(s) % 2 == 1 else 1::2]
>
> or something equally ugly.

You're assuming something here you haven't said.  The easiest way to
get '97531' is to type '97531' ;-)  If your agenda is the general
"return every 2nd element starting with the last element", then the
obvious way to do that under the proposal is to write [::-1][::2].
You can't seriously claim that's harder than the "[::2][::-1]" you
presented as the obvious way to "get the (B) result" given (A).


> (Also, (A) is the current behavior and switching to (B) would break any
> existing use of strides < -1.)

Did you notice that Guido titled this thread "Where did we go wrong
with negative stride?".;-)

BTW, do you have use cases for negative strides other than -1?  Not
examples, use cases.  There haven't been any in this thread yet.


More information about the Python-ideas mailing list