'Is there unstack in NumPy?
There is np.stack in NumPy, but is there an opposite np.unstack
same as tf.unstack?
Solution 1:[1]
Coming across this late, here is a much simpler answer:
def unstack(a, axis=0):
return np.moveaxis(a, axis, 0)
# return list(np.moveaxis(a, axis, 0))
As a bonus, the result is still a numpy array. The unwrapping happens if you just python-unwrap it:
A, B, = unstack([[1, 2], [3, 4]], axis=1)
assert list(A) == [1, 3]
assert list(B) == [2, 4]
Unsurprisingly, it is also the fastest:
# np.squeeze
? python -m timeit -s "import numpy as np; a=np.array(np.meshgrid(np.arange(1000), np.arange(1000)));" "C = [np.squeeze(e, 1) for e in np.split(a, a.shape[1], axis = 1)]"
100 loops, best of 5: 2.64 msec per loop
# np.take
? python -m timeit -s "import numpy as np; a=np.array(np.meshgrid(np.arange(1000), np.arange(1000)));" "C = [np.take(a, i, axis = 1) for i in range(a.shape[1])]"
50 loops, best of 5: 5.08 msec per loop
# np.moveaxis
? python -m timeit -s "import numpy as np; a=np.array(np.meshgrid(np.arange(1000), np.arange(1000)));" "C = np.moveaxis(a, 1, 0)"
100000 loops, best of 5: 3.89 usec per loop
# list(np.moveaxis)
? python -m timeit -s "import numpy as np; a=np.array(np.meshgrid(np.arange(1000), np.arange(1000)));" "C = list(np.moveaxis(a, 1, 0))"
1000 loops, best of 5: 205 usec per loop
Solution 2:[2]
Thanks to suggestion of @hpaulj solved task efficiently using np.split.
import numpy as np
def unstack(a, axis = 0):
return [np.squeeze(e, axis) for e in np.split(a, a.shape[axis], axis = axis)]
a = [np.array([[1,2,3],[4,5,6]]), np.array([[7,8,9],[10,11,12]])]
for axis in range(len(a[0].shape) + 1):
b = np.stack(a, axis)
c = unstack(b, axis)
# Check that we have same "c" as input "a"
assert len(c) == len(a) and all(np.all(sc == sa) for sc, sa in zip(c, a)), (c, a)
Solution 3:[3]
Can also be solved using np.take.
It is a simpler than this solution but could be a bit less efficient, needs timing measurement for different inputs.
import numpy as np
def unstack(a, axis = 0):
return [np.take(a, i, axis = axis) for i in range(a.shape[axis])]
a = [np.array([[1,2,3],[4,5,6]]), np.array([[7,8,9],[10,11,12]])]
for axis in range(len(a[0].shape) + 1):
b = np.stack(a, axis)
c = unstack(b, axis)
# Check that we have same "c" as input "a"
assert len(c) == len(a) and all(np.all(sc == sa) for sc, sa in zip(c, a)), (c, a)
Solution 4:[4]
it's simple like:
list(array)
it will iterate over the first axis.
an example:
a = np.array([1,2,3])
b = np.array([4,5,6])
c = np.stack([a,b])
d = list(c)
Output of c
array([[1, 2, 3],
[4, 5, 6]])
Output of d
[array([1,2,3]), array([4,5,6])]
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
Solution | Source |
---|---|
Solution 1 | Ivorius |
Solution 2 | |
Solution 3 | Arty |
Solution 4 | Gabriel Barbosa |