记录的电子束数据的二维反卷积

信息处理 fft 卷积
2022-02-02 00:57:49

我目前正在从事一个涉及使用电子枪的项目,如果知道从电子枪射出的电子的点形状(距离电子束中心某个 x、y 处的电子频率),那就太好了)。我们目前的假设是光束的光斑形状有点高斯。

我们有一个连接到探测器的皮安计,该探测器输出与撞击探测器的电子数量相对应的电流。检测器是具有一定半径 R 的圆形。

如果我没记错的话,扫描光束并记录皮安计的读数将产生一个矩阵,该矩阵是光束点形状的卷积和一个 2D 阶跃函数,该函数在 R 之外为 0,在 R 内为非零。我看过通过一些关于与具有高斯模糊的图像相关的反卷积的先前问题,看起来这非常相似,除了函数是阶跃函数而不是高斯函数。

我已经尝试使用 Matlab 的 conv2、FFT2 和 iFFT2 函数来获得该线程建议的反卷积,但它会产生如下所示的内容:

反卷积尝试

产生这个的代码是:

mu = [0 0]; 
Sigma = [1 0; 0 1]; 
x = -3:.2:3;
[X1,X2] = meshgrid(x,x);
F = mvnpdf([X1(:) X2(:)],mu,Sigma);
F = reshape(F,length(x),length(x));
for i=1:31
    for j=1:31 
        if x1(i)^2+x2(i)^2 >= 4 
            circ(i,j)=0; 
        else
            circ(i,j)=1; 
        end 
    end 
end 
conv = conv2(F,circ,'same');
D = ifft2( fft2(conv) ./ fft2(circ) ); 
surf(x1,x2,D);

尝试对阶跃函数进行反卷积是否存在固有问题?另外,我尝试使用全卷积,但这似乎产生了更奇怪的反卷积......

我只是以错误的方式解决这个问题吗?(我已经包含了 python,因为如果存在解决方案,我更愿意使用 python,但 matlab 也可以)

1个回答

您的去卷积方法似乎有效。下面是一些实现反卷积的 Gnu Octave(或多或少 Matlab)代码。

给它两个代表你的目标和你的光束的文件,它将执行两者的卷积,然后使用你的方法来反转卷积。
结果显示了原始的两个图像、卷积图像和恢复的光束形状。
附图显示了我的测试结果。

左上角是目标(50x50px)

左下方是光束(14x16px)

右上角是两者的卷积(电子计数图)

右下是恢复的光束形状

填充有点偏离,所以在恢复的图像中有一些环绕。不过,结果很清楚。

我会检查您用于光束和目标的图像,并检查卷积图像是否符合您的预期。部分问题也可能与您在卷积中使用的“相同”。这会返回与其中一张卷积图像大小相同的图像,这将导致您丢失大量信息。如果我使用“相同”,那么我根本不会得到恢复的形状。卷积后的图像大于两个图像中较大的一个,因此您必须使用“完整”然后填充目标图像来进行反卷积。


ETA:我忙于查看反卷积的细节,以至于忘记提及您对扫描光束穿过目标的效果的看法。

我同意这相当于将光束形状与目标形状进行卷积,因此我认为您在确定光束形状方面处于正确的轨道上 - 如果我不相信我不会费心检查反卷积.

当您实际进行扫描以确定光束形状时,您需要注意一些事项:

  1. 扫描区域 - 您需要过度扫描目标。将目标的半径作为 R,将光束的最大半径(估计)作为 r,那么您将需要扫描至少为 R*2+2*(r*2) 的正方形 - 实际上更多,但那是绝对最小值。由于您不知道光束形状(因此不知道其真实尺寸),因此最好在这里过分而不是重复测量
  2. 用于进行反卷积的图像必须(尽可能完美地)匹配目标的真实形状和大小。图像中目标形状的位置并不重要。
  3. 当您填充目标形状图像时,将图像居中填充。正如我所做的那样,填充都在顶部和左侧。这会将目标形状的右边缘和下边缘放在图像的边缘。舍入错误可以(并且确实,如您所见)导致图像的一部分环绕。由于您将创建图像,因此您可以只使用适当的边框创建图像,而不是在代码中填充它。

样本反卷积 target=imread("target.png"); beam=imread("beam.png"); convolved=real(fftconv2(target,beam,"full")); widthc=size(convolved,2); heightc=size(convolved,1); widtht=size(target,2); heightt=size(target,1); padw=int32(widthc-widtht); padh=int32(heightc-heightt); paddedtarget=padarray(target,[padh,padw],0,'pre'); recovered=real(ifft2(fft2(convolved)./fft2(paddedtarget))); subplot(2,2,1) imshow(single(target)); subplot(2,2,2) imshow(single(convolved)); subplot(2,2,3) imshow(single(beam)); subplot(2,2,4) imshow(single(recovered));