[英]flatten list of lists and scalars
因此对于矩阵,我们有numpy.flatten()之类的方法
np.array([[1,2,3],[4,5,6],[7,8,9]]).flatten()
给出[1,2,3,4,5,6,7,8,9]
如果我想从np.array([[1,2,3],[4,5,6],7])
为[1,2,3,4,5,6,7]
怎么办?
是否存在执行类似功能的现有功能?
对于不均匀的列表,数组是对象的dtype(和1d,因此,flatten不会更改它)
In [96]: arr=np.array([[1,2,3],[4,5,6],7])
In [97]: arr
Out[97]: array([[1, 2, 3], [4, 5, 6], 7], dtype=object)
In [98]: arr.sum()
...
TypeError: can only concatenate list (not "int") to list
7
要素给问题。 如果我将其更改为列表:
In [99]: arr=np.array([[1,2,3],[4,5,6],[7]])
In [100]: arr.sum()
Out[100]: [1, 2, 3, 4, 5, 6, 7]
我在这里使用技巧。 数组列表的元素以及列表[1,2,3]+[4,5]
的元素是串联的。
基本要点是对象数组不是二维数组。 在许多方面,它更像是列表列表。
最好的变平器是chain
In [104]: list(itertools.chain(*arr))
Out[104]: [1, 2, 3, 4, 5, 6, 7]
尽管它也会阻塞整数7版本。
如果数组是列表列表(不是列表和标量的原始组合),则np.concatenate
有效。 像在列表上一样在对象上进行迭代。
使用混合的原始列表进行concatenate
不起作用,但是hstack
In [178]: arr=np.array([[1,2,3],[4,5,6],7])
In [179]: np.concatenate(arr)
...
ValueError: all the input arrays must have same number of dimensions
In [180]: np.hstack(arr)
Out[180]: array([1, 2, 3, 4, 5, 6, 7])
那是因为hstack
首先遍历列表,并确保所有元素都是atleast_1d
。 这种额外的迭代使其更健壮,但会增加处理速度。
In [170]: big1=arr.repeat(1000)
In [171]: timeit big1.sum()
10 loops, best of 3: 31.6 ms per loop
In [172]: timeit list(itertools.chain(*big1))
1000 loops, best of 3: 433 µs per loop
In [173]: timeit np.concatenate(big1)
100 loops, best of 3: 5.05 ms per loop
大小的两倍
In [174]: big1=arr.repeat(2000)
In [175]: timeit big1.sum()
10 loops, best of 3: 128 ms per loop
In [176]: timeit list(itertools.chain(*big1))
1000 loops, best of 3: 803 µs per loop
In [177]: timeit np.concatenate(big1)
100 loops, best of 3: 9.93 ms per loop
In [182]: timeit np.hstack(big1) # the extra iteration hurts hstack speed
10 loops, best of 3: 43.1 ms per loop
sum
是平方的
res=[]
for e in bigarr:
res += e
res
随着e的数量而增长,因此每个迭代步骤都更加昂贵。
chain
时代最好。
您可以使用yield编写自定义展平函数:
def flatten(arr):
for i in arr:
try:
yield from flatten(i)
except TypeError:
yield i
用法示例:
>>> myarr = np.array([[1,2,3],[4,5,6],7])
>>> newarr = list(flatten(myarr))
>>> newarr
[1, 2, 3, 4, 5, 6, 7]
您可以在此处使用apply_along_axis
>>> arr = np.array([[1,2,3],[4,5,6],[7]])
>>> np.apply_along_axis(np.concatenate, 0, arr)
array([1, 2, 3, 4, 5, 6, 7])
另外,列表的数量也不是二次方。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.