我有一个3D矩阵,想要计算这个矩阵的梯度。我做的唯一一步是为2D图像定义图像渐变,如下所示:
sx = [-1 0 1; -2 0 2; -1 0 1];
sy = [1 2 1; 0 0 0; -1 -2 -1];
Gx = conv2(input, sx, 'same');
Gy = conv2(input, sy, 'same');
grdmg = sqrt(Gx.^2+Gy.^2);
grddr = atan2(Gy,Gx);
我想知道如何将此代码扩展到3D?我知道在3D矩阵中我应该使用convn,但不知道我应该如何更改sx,sy和make sz。
答案 0 :(得分:1)
如果您想计算3D渐变,您还必须制作内核3D。您不仅要检查矩阵的i th 切片中的更改,还需要检查(i-1) th 切片和(i + 1) ) th 切片。
作为次要评论,sy
应该是sx
的转置,但您不会在此处。确保在做任何事情之前更改此内容。
此外,通过添加维度,您有三个更多可能的内核,因为您需要在每个切片中水平检查更改,在每个切片中垂直检查,或者暂时。因此,您只需通过沿第三维复制sz
三次,或沿第三维复制sx
三次或制作第一个切片所在的时间内核来制作sy
。全部1,第二个切片全部为零,第三个切片全部为-1。因此,调用所有这些内核szx
,szy
和szz
,您可以将它们创建为:
szx = cat(3, sx, sx, sx);
szy = cat(3, sy, sy, sy);
szz = cat(3, ones(3,3), zeros(3,3), -ones(3,3));
要计算幅度,您只需找到所有这些组件的大小,然后按照建议使用convn
:
Gx = convn(input, szx, 'same');
Gy = convn(input, szy, 'same');
Gz = convn(input, szz, 'same');
grdmg = sqrt(Gx.^2 + Gy.^2 + Gz.^2);
至于角度,这是非常模糊的,因为你现在有三个组件,如果你想找到角度,你需要在3D空间中有两个向量,并找到这两个向量之间的角度。对于2D,这已经很好地定义,因为您已经创建了2个向量,因此角度只是垂直和水平分量之间的arctan
。由于您有三个组件,并且有两个组件可供选择,因此您可以计算三种可能的角度,每个角度都与x
,y
或z
轴相关。
在这种情况下,我没有为您提供答案,但Math StackExchange中的这个特定示例可以让您进一步了解如何使用3D渐变计算角度。重要的一点是,您需要知道相对于哪个轴测量角度。
https://math.stackexchange.com/questions/569019/how-do-you-get-3d-gradient-direction-and-magnitude