如何应用高斯滤波器在matlab中的图像的单个像素?

问题描述:

我有一个白色/黑色的图像。我想对此图像上的白色像素应用高斯滤镜。但是,我想逐像素地应用它,因为我想给不同的像素提供不同的高斯带宽参数。如何应用高斯滤波器在matlab中的图像的单个像素?

例如,图像上只有2个像素是白色的,其他的是黑色的。我想对这2个像素应用不同的高斯滤镜。假设X [2]和Y [2]是2个像素的坐标。

Gaussian bandwidth for X[0] and Y[0] is [10, 10], standard deviation is 1. 
Gaussian bandwidth for X[1] and Y[1] is [20, 20], standard deviation is 3. 

我知道roifilt2会在ROI上工作,但它似乎只适用于图像区域而不是单个像素。我已经通过我的理解编码后,我检查ROI处理,但下面的代码给我错误:

Error using imwrite (line 422) 
Image data can not be empty. 

Error in guassianFilter (line 73) 
    imwrite(out,[outdir,imname,'.png'],'png'); 

看来滤波输出图像是空的。但我是matlab新手,我不知道为什么会发生这种情况,以及如何解决这个问题。 :(

是否有任何MATLAB函数,我可以直接打电话到做的工作

代码:

while ischar(tline) 
     line = regexp(tline,' ','split'); 
     if(strcmp(line{1},'touch') == 1) 
      c = floor(str2double(line{1,3})); % same as X[0] as I mentioned above 
      r = floor(str2double(line{1,4})); % same as Y[0] as I mentioned above 
      BW = roipoly(im,c,r); 
      G = fspecial('gaussian',[10 10],1); 
      out = roifilt2(G,im,BW); 
     end 
     if(strcmp(line{1},'dT') == 1) 
      c = floor(str2double(line{1,3})); % same as X[1] as I mentioned above 
      r = floor(str2double(line{1,4})); % same as X[1] as I mentioned above 
      BW = roipoly(im,c,r); 
      G = fspecial('gaussian',[20 20], 3); 
      out = roifilt2(G,im,BW); 
     end 
     tline = fgets(fid); 
    end 
    fclose(fid); 

    imname=strtok(imList(cnt).name,'.'); 
    imwrite(out,[outdir,imname,'.png'],'png'); 

概述一个想法,应该工作之前,让我看到一个问题的代码你发布了,看看你对roifilt2的调用,你会发现out被你从文件中读取的每个单像素指令的结果覆盖,即使你发现了一些导致空的结果图像的其他bug,结果永远不会复合材料。

这个怎么样。您可以首先从文件中读取所有像素位置和相应的带宽,然后从这些坐标中单独以两个笔划重建滤波后的图像。读取像素列表可以像这样

fid = fopen('points.txt'); 
pxl = struct('x', {}, 'y', {}, 'sig', {}); 
n_pxl = 0; 
tline = fgets(fid); 
while ischar(tline) 
    line = regexp(tline,' ','split'); 
    n_pxl = n_pxl + 1; 
    pxl(n_pxl).x = floor(str2double(line{1,3})); 
    pxl(n_pxl).y = floor(str2double(line{1,4})); 
    if strcmp(line{1},'touch') == 1 
     pxl(n_pxl).sig = 1; 
    elseif strcmp(line{1},'dT') == 1 
     pxl(n_pxl).sig = 3; 
    else 
     pxl(n_pxl).sig = nan; 
    end 
    tline = fgets(fid); 
end 
fclose(fid); 

其中xy是位置和sig是带宽。假设WIDTHHEIGHT是图像的尺寸,可以将复合结果图像初始化为平坦的out = zeros(HEIGHT, WIDTH);。筛选器大小的查找矢量可能为flt_size = [10, 15, 20];。在一些for -loop超过sig = [1, 3],我们创建的每个覆盖的“滑动”,收集对应于一个特定的西格玛

im_raw = zeros(HEIGHT, WIDTH); 
for k = find([pxl.sig] == sig) 
    im_raw(pxl(k).y, pxl(k).x) = 1; 
end 

的所有像素并递增复合与过滤操作的结果后

fsz = flt_size(sig); 
out = out + conv2(im_raw, fspecial('gaussian', [fsz, fsz], sig), 'same'); 

总之,循环将可能是这样的:

out = zeros(HEIGHT, WIDTH); 
flt_size = [10, 15, 20]; 
for sig = [1, 3] 
    im_raw = zeros(HEIGHT, WIDTH); 
    for k = find([pxl.sig] == sig) 
     im_raw(pxl(k).y, pxl(k).x) = 1; 
    end 
    fsz = flt_size(sig); 
    out = out + conv2(im_raw, fspecial('gaussian', [fsz, fsz], sig), 'same'); 
end 

使用稍大的带宽用于说明,H举个例子,每个类别有两点。左侧和中间图像显示每个“幻灯片”,右侧图像显示复合。每个图像显示为imagesc

Example

+0

非常感谢你支持!我非常感谢您的时间和精力,使其能够理解清楚。 – Jasmine