检查矩阵是否是 3d 数组元素的最快方法是什么?

What is the fastest way to check if a matrix is an element of an 3d array?

我有一个仅由 0 和 1 组成的 3d 二进制数组 M(x,y,z),然后在每个时间步给我一个二进制矩阵 A(x,y),然后我需要检查 A (x,y)=M(x,y,z) 对于一些 z,如果不是,那么我将它添加到 M 的末尾,M(x,y,end+1)=A(x,y)。有没有比检查每个 z 直到找到相等更快的方法来做到这一点?

我尝试遍历每个 z,但后来我认为应该可以预先计算出 M 的某些内容,使我们可以通过 1 次比较检查多个 z。

显然,如果不检查所有这些,就无法做到这一点。

但是,如果您想找到一种更快的方法,我们可以借鉴图像处理文献中使用“图像积分”的地方。 只需为每个 z 切片计算 sum(M,[1,2]) 并将其存储在数组中。当一个新的 A 出现时,计算 sum(A(:)) 并与列表进行比较。然后只完全比较 z 与新矩阵积分匹配的索引。

根据矩阵的性质,您可能需要找到一个非积分的不同度量,因为您的应用程序可能会生成归一化矩阵或类似矩阵。只需找到一个足够不同且易于计算的指标即可。图像积分对于自然图像非常有用。

过早的优化是万恶之源,我不会尝试做任何花哨的事情,而是简单地尝试使用 MATLAB 的数组表示法和矢量化,然后再担心优化。我还没有测试过,但很有可能只是向量化的东西是非常合理的,因为它使内存访问所需的统一。这是我的做法:

>> M = rand(3,4,7) > 0.5;  % Example data
>> A1 = rand(3,4) > 0.5;   % (Probably) not a page of M
>> A2 = M(:,:,3);          % Page 3 of M
>> find(all(A1==M, [1 2])) % Use implicit expansion to compare
ans =
  0x1 empty double column vector
>> find(all(A2==M, [1 2]))
ans =
     3

这在 Ax == M 片段中使用隐式扩展(在 R2016b 中引入),然后在 all 中使用相对较新的(在 R2018b 中引入)矢量化维度说明符作为“缩减”片段。

根据@Wolfie 的评论,如果您只需要知道 是否存在 (而不是位置)页面,则可以使用 any 而不是 find

if any(all(A2==M, [1 2]))
    % Page was present
else
    % Page not already present
end