I have a 2d array that looks like this:
>>> X
array([[10, 15],
[20, 25],
[30, 35],
[40, 45],
[50, 55],
[60, 65],
[70, 75],
[80, 85],
[90, 95]])
>>> X.shape
(9, 2)
My goal is to make a new 3d array with 3 steps per every row:
>>> Y
array([[[10, 15],
[20, 25],
[30, 35]],
[[20, 25],
[30, 35],
[40, 45]],
[[30, 35],
[40, 45],
[50, 55]],
[[40, 45],
[50, 55],
[60, 65]],
[[50, 55],
[60, 65],
[70, 75]],
[[60, 65],
[70, 75],
[80, 85]],
[[70, 75],
[80, 85],
[90, 95]]])
>>> Y.shape
(7, 3, 2)
I'd like to know if there are any simple way to do this, without using loops.
CodePudding user response:
A pure numpy solution would be to use numpy.lib.stride_tricks.sliding_window_view
:
from numpy.lib.stride_tricks import sliding_window_view
new_a = sliding_window_view(a, window_shape=(3,2)).reshape(7, 3, 2)
Output:
>>> new_a
array([[[10, 15],
[20, 25],
[30, 35]],
[[20, 25],
[30, 35],
[40, 45]],
[[30, 35],
[40, 45],
[50, 55]],
[[40, 45],
[50, 55],
[60, 65]],
[[50, 55],
[60, 65],
[70, 75]],
[[60, 65],
[70, 75],
[80, 85]],
[[70, 75],
[80, 85],
[90, 95]]])
CodePudding user response:
It's very easy to do with Pandas, using DataFrame.rolling
:
df = pd.DataFrame(a)
new_a = np.array([w.to_numpy() for w in df.rolling(3) if len(w) == 3])
Output:
>>> new_a
array([[[10, 15],
[20, 25],
[30, 35]],
[[20, 25],
[30, 35],
[40, 45]],
[[30, 35],
[40, 45],
[50, 55]],
[[40, 45],
[50, 55],
[60, 65]],
[[50, 55],
[60, 65],
[70, 75]],
[[60, 65],
[70, 75],
[80, 85]],
[[70, 75],
[80, 85],
[90, 95]]])