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

Joshua Landau joshua at landau.ws
Mon Oct 28 22:06:25 CET 2013


On 28 October 2013 17:15, Joshua Landau <joshua at landau.ws> wrote:
> <suggested using "~" instead of "-">

# Here's a quick mock-up of my idea.

class NotSliced(list):
    def __getitem__(self, itm):
        if isinstance(itm, slice):
            start, stop, step = itm.start, itm.stop, itm.step

            if start is None: start = 0
            if stop  is None: stop  = ~0
            if step  is None: step  = 1

            if start < 0: start += len(self) + 1
            if stop  < 0: stop  += len(self) + 1

            if step > 0:
                return NotSliced(super().__getitem__(slice(start, stop, step)))

            else:
                return NotSliced(super().__getitem__(slice(stop,
start))[::step])

        else:
            return super().__getitem__(itm)

ns = NotSliced([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])

[ns[i] for i in range(10)]
#>>> [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

# See why this is a much better mapping?
[list(ns)[-i] for i in range(10)]
[ns[~i] for i in range(10)]
#>>> [0, 9, 8, 7, 6, 5, 4, 3, 2, 1]
#>>> [9, 8, 7, 6, 5, 4, 3, 2, 1, 0]

ns[~6:7]
list(ns)[-6:7]
#>>> [4, 5, 6]
#>>> [4, 5, 6]

ns[~4:~0][::-1]
ns[~0:~4:-1]
#>>> []
#>>> [9, 8, 7, 6]

ns[~4:~0][::-2]
ns[~0:~4:-2]
#>>> []
#>>> [9, 7]


# Here's something that makes me really feel this is natural.

ns[2:~2]
#>>> [2, 3, 4, 5, 6, 7]

ns[1:~1]
#>>> [1, 2, 3, 4, 5, 6, 7, 8]

ns[0:~0]
#>>> [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

# VERSUS (!!!)

[0, 1, 2, 3, 4, 5, 6, 7, 8, 9][2:-2]
#>>> [2, 3, 4, 5, 6, 7]

[0, 1, 2, 3, 4, 5, 6, 7, 8, 9][1:-1]
#>>> [1, 2, 3, 4, 5, 6, 7, 8]

[0, 1, 2, 3, 4, 5, 6, 7, 8, 9][0:-0]
#>>> []



# And some more...

ns[~6:6:+1]
ns[6:~6:-1]
#>>> [4, 5]
#>>> [5, 4]

[0, 1, 2, 3, 4, 5, 6, 7, 8, 9][-6:6:+1]
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9][6:-6:-1]
#>>> [4, 5]
#>>> [6, 5]



# Surely you agree this is much more intuitive.


# Another example from the thread

a = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
for n in reversed(range(7)):
    print(n, a[:-n])
#>>> 6 [0, 1, 2, 3]
#>>> 5 [0, 1, 2, 3, 4]
#>>> 4 [0, 1, 2, 3, 4, 5]
#>>> 3 [0, 1, 2, 3, 4, 5, 6]
#>>> 2 [0, 1, 2, 3, 4, 5, 6, 7]
#>>> 1 [0, 1, 2, 3, 4, 5, 6, 7, 8]
#>>> 0 []

for n in reversed(range(7)):
    print(n, ns[:~n])
#>>> 6 [0, 1, 2, 3]
#>>> 5 [0, 1, 2, 3, 4]
#>>> 4 [0, 1, 2, 3, 4, 5]
#>>> 3 [0, 1, 2, 3, 4, 5, 6]
#>>> 2 [0, 1, 2, 3, 4, 5, 6, 7]
#>>> 1 [0, 1, 2, 3, 4, 5, 6, 7, 8]
#>>> 0 [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]


More information about the Python-ideas mailing list