![](/img/trans.png)
[英]Python and numpy : subtracting line by line a 2-dim array from a 1-dim array
[英]From a 1-dim array of bits obtain a particular 2-dim array of sequences of ones [Python]
我正在使用Python,我需要找到執行以下任務的最有效方法。
任務:給定零和一的任何一維數組v ,用k > = 0表示v的全部1的子序列數。
我需要從v獲得一個二維數組w :
1)shape(w)=(k,len(v)),
2)對於每個i = 1,..,k,“ w”的第i行是全零的數組,除了v的所有i的第i個子序列。
讓我舉一個例子:假設$ v $是數組
v=[0,1,1,0,0,1,0,1,1,1]
那么k = 3並且w應該是數組
w=[[0,1,1,0,0,0,0,0,0,0],[0,0,0,0,0,1,0,0,0,0],[0,0,0,0,0,0,0,1,1,1]]
可以編寫代碼以多種方式執行此任務,例如:
import numpy as np
start=[]
end=[]
for ii in range(len(v)-1):
if (v[ii:ii+2]==[0,1]).all():
start.append(ii)
if (v[ii:ii+2]==[1,0]).all():
end.append(ii)
if len(start)>len(end):
end.append(len(v)-1)
w=np.zeros((len(start),len(v)))
for jj in range(len(start)):
w[jj,start[jj]+1:end[jj]+1]=np.ones(end[jj]-start[jj])
但是我需要在非常大的數組v上執行此任務,並且此任務是函數的一部分,然后將其最小化..因此,我需要它盡可能高效和快速。
因此,總而言之,我的問題是:用Python執行計算最有效的方法是什么?
這是一種矢量化方式-
def expand_islands2D(v):
# Get start, stop of 1s islands
v1 = np.r_[0,v,0]
idx = np.flatnonzero(v1[:-1] != v1[1:])
s0,s1 = idx[::2],idx[1::2]
# Initialize 1D id array of size same as expected o/p and has
# starts and stops assigned as 1s and -1s, so that a final cumsum
# gives us the desired o/p
N,M = len(s0),len(v)
out = np.zeros(N*M,dtype=int)
# Setup starts with 1s
r = np.arange(N)*M
out[s0+r] = 1
# Setup stops with -1s
if s1[-1] == M:
out[s1[:-1]+r[:-1]] = -1
else:
out[s1+r] = -1
# Final cumsum on ID array
out2D = out.cumsum().reshape(N,-1)
return N, out2D
樣品運行-
In [105]: v
Out[105]: array([0, 1, 1, 0, 0, 1, 0, 1, 1, 1])
In [106]: k,out2D = expand_islands2D(v)
In [107]: k # number of islands
Out[107]: 3
In [108]: out2D # 2d output with 1s islands on different rows
Out[108]:
array([[0, 1, 1, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 1, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 1, 1, 1]])
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.