Slice a list or NumPy array into consecutive tuples My function needs two params(a,b) and if...break, which seems redundant. Can it be made prettier?

def slice_list(lst,num):
    """
    Given a list or Numpy array，
    get consecutive tuples based on specific window. 
    """
    rst = []
    for i,_ in enumerate(lst):
        a = i
        b = i + num
        if len(lst[a:b])&lt;num:
            break
        rst.append(tuple(lst[a:b]))
    return rst


Example:

&gt;&gt;&gt; lst = np.array([10, 11, 12, 13, 26, 28])
&gt;&gt;&gt; slice_list(lst,4)
[(10, 11, 12, 13), (11, 12, 13, 26), (12, 13, 26, 28)]
I believe that what you are looking for is already available as an itertools recipe; even though pairwise only allow you to return couples and not tuple of arbitrary length.

You will need to modify it so that:


tee will return num iterators;
you advance each of these iterators by one more element than the previous one (see the consume recipe for that).


This can lead to the following code:

import itertools


def advance(iterator, step):
    next(itertools.islice(iterator, step, step), None)


def tuplewize(iterable, size):
    iterators = itertools.tee(iterable, size)
    for position, iterator in enumerate(iterators):
        advance(iterator, position)
    return zip(*iterators)


Usage being:

&gt;&gt;&gt; for t in tuplewize(lst, 4):
...   print(t)
... 
(10, 11, 12, 13)
(11, 12, 13, 26)
(12, 13, 26, 28)




However, you are using numpy so we may come up with a better numpy approach:


numpy.roll allows us to advance the nth element on top of the list;
numpy.stack allows us to concatenate the rolled arrays into a single 2D array;
numpy.transpose allows us to convert a "list of lists" into a "list of tuples".


Full code being:

import numpy as np


def tuplewize(array, size):
    if size &lt; 2:
        return np.array([array])

    stack = np.stack([np.roll(array, -i) for i in range(size)])
    return np.transpose(stack)[:-size+1]


Usage being:

&gt;&gt;&gt; tuplewise(lst, 4)
array([[10, 11, 12, 13],
       [11, 12, 13, 26],
       [12, 13, 26, 28]])




And as @Peilonrayz indicated in a comment, a third possibility is to use the more_itertools package and its windowed function which has extended capabilities; and as such more overhead, so depending on your needs it may or may not suit you.