我是matlab和图像处理的新手,我有一些正常化的问题,但我不确定原因。
在我的代码中,我将图像存储为lim3中的黑白图像,然后:
minvalue = min(min(min(lim3)));
maxvalue = max(max(max(lim3)));
normimg = (lim3-minvalue)*255/(maxvalue-minvalue);
不幸的是,这给出了一个与lim3完全相同的新图像,但我不确定为什么。理想情况下,我不想使用histeq函数,所以如果有人可以解释如何修复此代码以使其工作,我将不胜感激。
答案 0 :(得分:3)
评论中的所有人都提出了非常好的观点,但如果你想要tl;dr
答案,这里是最重要的一点:
如果所有颜色通道的最小值和最大值分别为0
和255
,则表示最小和最大颜色值为黑白分别。如果您的图像是单通道图像/灰度,则情况相同。因此,如果您尝试对输出图像进行标准化,它将与您乘以并除以相同比例相同。但是,作为次要注释,如果您的图像是灰度,则上述代码将起作用。我也会摆脱多余的嵌套min
/ max
来电。
在进行此缩放之前,您需要确保将图像强制转换为double
,因为您很可能会生成浮点数。如果您的比例为< 1
,则会无意中将其截断为0.通常,当您尝试将强度标准化时,您将失去精确度,因为图像的类型最有可能uint8
。您还需要记住在完成后再回到uint8
,因为这是您投射前图像的原始类型。您可以执行此投射,也可以使用im2double
,因为这基本上可以根据您的需要进行操作,但会将图像的强度标准化为[0,1]
的范围。
因此,如果你真的真的...真的...想要使用上面的代码,你必须做这样的事情:
lim3 = double(lim3); %// Cast to double
minvalue = min(lim3(:)); %// Note the change here
maxvalue = max(lim3(:)); %// Got rid of superfluous nested min/max calls
normimg = uint8((lim3-minvalue)*255/(maxvalue-minvalue)); %// Cast back to uint8
如果您正在阅读的图片是灰度,此代码将有效。
但是,如果您想将上述内容应用于彩色图像,我建议您不要使用上述方法。原因是你只会看到差异如果每个颜色平面的最小值和最大值分别相同 - 分别为0和255。我建议你做的是分别标准化每个颜色平面,这样你就可以将每个颜色平面推到[0,1]
的范围内,而不是仅限于最小值和最大值。一个颜色的飞机。
因此,我建议你做这样的事情:
lim3 = double(lim3); %// Cast to double
normimg = uint8(zeros(size(lim3))); %// Allocate output image
for idx = 1 : 3
chan = lim3(:,:,idx);
minvalue = min(chan(:));
maxvalue = max(chan(:));
normimg(:,:,idx) = uint8((chan-minvalue)*255/(maxvalue-minvalue)); %// Cast back to uint8
end
上面的代码分别访问每个颜色平面,对平面进行标准化,然后将结果放在输出图像normimg
中。如果你想看到彩色图像的任何对比度差异,我建议你使用上面的方法。