我正在尝试整合我的数据深度。我的数据是4D数据(341,50,120,100),其中我分别有时间,深度,i-pos,j-pos。我正在尝试应用以下等式....
Vf[t,i,j] = integral ((mean - data[t,zz,i,j]) x mean) x ( depth[zz,i,j] - depth[zz+1,i,j])
其中,
f = (mean - data)*mean
d_depth, i.e: abs(data[0,0,0,0]-data[0,1,0,0])
因此,
Vf = integral(f*d_depth)
尽管如此,我正在做的事情并不是那么有效。
for tt in range(sal.shape[0]):
print('time',str(tt))
for j in range(sal.shape[3]):
print('j',str(j))
for i in range(sal.shape[2]):
print('i',str(i))
for zz in range(sal.shape[1]-1):
Vf[tt,i,j] += abs(grid[zz,i,j]-grid[zz+1,i,j])*f[tt,zz,i,j]
有人会知道如何以更好的方式做到这一点吗?
谢谢,
马修斯
答案 0 :(得分:0)
从你的代码中划分我假设
f
有4个维度:tt
,zz
,i
,j
grid
有3个维度:zz
,i
,j
Vf
有3个维度:tt
,i
,j
虚假数据:
TT = 5
ZZ = 3
I = 5
J = 4
grid = np.random.randint(0, 255, (ZZ, I, J))
f = np.random.rand(TT,ZZ,I,J)
嵌套for循环可以矢量化:
abs(grid[zz,i,j]-grid[zz+1,i,j])
在第一个轴上基本上是numpy.diff(),可以在没有循环的情况下在完整数组上执行。
term1 = np.absolute(np.diff(grid, axis = 0))
term1
的形状是(ZZ-1,I,J)。为了将其乘以f
,zz
维度必须相同,以便f
tt
维度/轴上的乘法broadcast 。从最里面的循环语句中,我们看到zz
的最后一个元素未被使用 - for zz in range(sal.shape[1]-1):
。
w = term1 * f[:,:-1,...]
从Vf[tt,i,j] +=
我们看到zz
轴已消失,因此它正在对zz
轴进行求和。
vf = w.sum(axis = 1)
...
term1 = np.absolute(np.diff(grid, axis = 0))
w = term1*f[:,:-1,...]
vf = w.sum(axis = 1)
通过嵌套for循环运行我的假数据:
Vf = np.zeros((TT,I,J))
for tt in range(TT):
## print('time',str(tt))
for j in range(J):
## print('j',str(j))
for i in range(I):
## print('i',str(i))
for zz in range(ZZ-1):
Vf[tt,i,j] += abs(grid[zz,i,j]-grid[zz+1,i,j])*f[tt,zz,i,j]
将v
与Vf
进行比较表示结果相同:
>>> np.all(Vf == vf)
True
>>>
有一些 einsum 等价物有时会更快。
w = term1*f[:,:-1,...]
可以替换为
w = np.einsum('ijkl, ijkl->ijkl',f[:,:-1,...], term1[None,...])
和vf = w.sum(axis = 1)
可以替换为
vf = np.einsum('wxyz->wyz', w)
将操作组合到单个einsum会产生明显的加速
vf = np.einsum('ijkl, ijkl->ikl',f[:,:-1,...], term1[None,...])