Matlab:256个二进制矩阵到一张256级灰度图像
我的一个过程产生 256 个二进制(逻辑)矩阵,每个矩阵对应灰度源图像的每一级。
代码如下:
so = imread('bio_sd.bmp');
co = rgb2gray(so);
for l = 1:256
bw = (co == l); % Binary image from level l of original image
be = ordfilt2(bw, 1, ones(3, 3)); % Convolution filter
bl(int16(l)) = {bwlabel(be, 8)}; % Component labelling
end
我获得了 256 个二值图像的元胞数组。如果该位置处的源图像像素与二值图像的索引具有相同的级别,则此类二值图像包含 1。
IE。二进制图像 bl{12} 包含 1,其中源图像的像素级别为 12。
我想通过将 256 个二进制矩阵组合回灰度图像来创建新图像。
但我对 Matlab 很陌生,我想知道是否有人可以帮我编码:)
ps:我使用的是 matlab R2010a 学生版。
a process of mine produces 256 binary (logical) matrices, one for each level of a grayscale source image.
Here is the code :
so = imread('bio_sd.bmp');
co = rgb2gray(so);
for l = 1:256
bw = (co == l); % Binary image from level l of original image
be = ordfilt2(bw, 1, ones(3, 3)); % Convolution filter
bl(int16(l)) = {bwlabel(be, 8)}; % Component labelling
end
I obtain a cell array of 256 binary images. Such a binary image contains 1s if the source-image pixel at that location has the same level as the index of the binary image.
ie. the binary image bl{12} contains 1s where the source image has pixels with the level 12.
I'd like to create new image by combining the 256 binary matrices back to a grayscale image.
But i'm very new to Matlab and i wonder if someone can help me to code it :)
ps : i'm using matlab R2010a student edition.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
最简单的解决方案是依次迭代每个逻辑矩阵,将其乘以相应的权重,然后累加到代表最终图像的输出矩阵中。
The simplest solution would be to iterate through each of your logical matrices in turn, multiply it by its corresponding weight, and accumulate into an output matrix which will represent your final image.
你的代码做了什么......
我认为最好首先检查一下你发布的代码实际上在做什么,因为存在一些不一致的地方。我将遍历循环中的每一行:
bw = (co == l);
这只是创建一个二进制矩阵
bw
,其中灰度图像co
的像素强度等于循环值l
。我注意到你从 1 循环到 256,这让我觉得很奇怪。通常,加载到 MATLAB 中的图像将是无符号8位整数类型,意味着灰度值的范围为0到255在这种情况下,当l = 256
时计算的最后一个二进制矩阵bw
将始终包含全零。另外,您不对灰度级为 0 的像素进行任何处理。从后续处理来看,我猜测您故意要忽略灰度值 0,在这种情况下,您可能只需要从 1 循环到 255 .be = ordfilt2(bw, 1, Ones(3, 3));
您在这里使用 ORDFILT2 执行的操作实质上是执行二元腐蚀操作。
bw
中任何以 0 作为其 8 个邻居之一的 1 值都将被设置为 0,从而导致 1 岛被侵蚀(即尺寸缩小)。由 1 组成的小岛将会消失,只留下具有相同灰度级别的较大的连续像素簇。bl(int16(l)) = {bwlabel(be, 8)};
这里您可能存在一些误解。首先,
bl
中的矩阵不是 逻辑矩阵。在您的示例中,函数 BWLABEL 将找到 8-连接的。找到的第一个簇的元素在输出图像中标记为 1,找到的第二个簇的元素标记为 2,等等。因此,矩阵将包含正整数值,其中 0 代表背景。其次,您打算将这些标记的簇用于任何用途吗?您可能需要进行进一步的处理,需要在给定的灰度强度级别上识别单独的簇,但关于从
bl
中的元素创建灰度图像,特定标签 值 是不必要的。您只需要识别零值和非零值,因此,如果您不使用 bl 进行其他任何操作,我建议您只需将be
的各个值保存在元胞数组并使用它们重新创建灰度图像。现在,给出答案...
一个非常简单的解决方案是使用函数 CAT,然后使用函数 MAX 查找沿第三维(对应于原始图像的灰度值)出现非零值的索引。对于给定的像素,如果沿第三维没有找到非零值(即全为零),那么我们可以假设该像素值应该为 0。但是, MAX 将默认为 1,因此您必须使用最大值作为逻辑索引来设置像素为 0:
请注意,为了显示或保存您可能想要更改结果图像类型的图像< code>grayImage 转换为无符号 8 位整数类型,如下所示:
What your code does...
I thought it may be best to first go through what the code you posted is actually doing, since there are a couple of inconsistencies. I'll go through each line in your loop:
bw = (co == l);
This simply creates a binary matrix
bw
with ones where your grayscale imageco
has a pixel intensity equal to the loop valuel
. I notice that you loop from 1 to 256, and this strikes me as odd. Typically, images loaded into MATLAB will be an unsigned 8-bit integer type, meaning that the grayscale values will span the range 0 to 255. In such a case, the last binary matrixbw
that you compute whenl = 256
will always contain all zeroes. Also, you don't do any processing for pixels with a grayscale level of 0. From your subsequent processing, I'm guessing you purposefully want to ignore grayscale values of 0, in which case you probably only need to loop from 1 to 255.be = ordfilt2(bw, 1, ones(3, 3));
What you are essentially doing here with ORDFILT2 is performing a binary erosion operation. Any values of 1 in
bw
that have a 0 as one of their 8 neighbors will be set to 0, causing islands of ones to erode (i.e. shrink in size). Small islands of ones will disappear, leaving only the larger clusters of contiguous pixels with the same grayscale level.bl(int16(l)) = {bwlabel(be, 8)};
Here's where you may be having some misunderstandings. Firstly, the matrices in
bl
are not logical matrices. In your example, the function BWLABEL will find clusters of 8-connected ones. The first cluster found will have its elements labeled as 1 in the output image, the second cluster found will have its elements labeled as 2, etc. The matrices will therefore contain positive integer values, with 0 representing the background.Secondly, are you going to use these labeled clusters for anything? There may be further processing you do for which you need to identify separate clusters at a given grayscale intensity level, but with regard to creating a grayscale image from the elements in
bl
, the specific label value is unnecessary. You only need to identify zero versus non-zero values, so if you aren't usingbl
for anything else I would suggest that you just save the individual values ofbe
in a cell array and use them to recreate a grayscale image.Now, onto the answer...
A very simple solution is to concatenate your cell array of images into a 3-D matrix using the function CAT, then use the function MAX to find the indices where the non-zero values occur along the third dimension (which corresponds to the grayscale value from the original image). For a given pixel, if there is no non-zero value found along the third dimension (i.e. it is all zeroes) then we can assume the pixel value should be 0. However, the index for that pixel returned by MAX will default to 1, so you have to use the maximum value as a logical index to set the pixel to 0:
Note that for the purposes of displaying or saving the image you may want to change the type of the resulting image
grayImage
to an unsigned 8-bit integer type, like so:整个答案仅适用于问题的原始形式。
让我们假设您可以获得所有内容将您的二进制矩阵组合成一个大的 n×m×256 矩阵
binaryimage(x,y,greyvalue)
。然后你可以计算你的最终图像,这里的魔法是由 bsxfun 完成的,它将 3D (nxmx 256) 二值图像与包含灰度值 0...255 的 1 x 1 x 256 向量相乘。这会生成一个 3D 图像,其中对于固定的 x 和 y,向量 (y,x,:) 包含许多零,并且(对于一个灰度值
G
,其中二进制图像包含1< /code>)它包含值
G
。因此,现在您只需对第三个维度求和即可获得nx m
图像。更新
为了测试其是否正常工作,我们首先采用另一种方式:
是随机灰度图像。您可以像这样计算 256 个二进制矩阵:
我们现在可以应用上面给出的解决方案
并验证我是否返回原始图像:
它给出
1
(true) :-)。更新 2
您现在提到您的二进制图像位于元胞数组中,我假设
binimg{1:256}
,每个元胞包含一个 nxm 二进制数组。如果可以的话,更改生成此数据的代码以创建我上面使用的 3D 二进制数组可能是有意义的 - 如果不同的单元格包含不同类型、形状或大小的数据,则单元格最有用。如果有充分的理由坚持使用元胞数组,您可以
使用上面使用的
n
和m
将其转换为 3D 数组。如果您已有size(binimg)==[1 256]
,则无需进行内部重塑。总而言之,您需要使用元胞数组binimg
来计算 3D 矩阵二值图像,然后您可以使用它来计算您感兴趣的newimage
我的答案开头的代码。希望这有帮助...
this whole answer only applies to the original form of the question.
Lets assume you can get all your binary matrices together into a big n-by-m-by-256 matrix
binaryimage(x,y,greyvalue)
. Then you can calculate your final image asThe magic here is done by bsxfun, which multiplies the 3D (n x m x 256) binaryimage with the 1 x 1 x 256 vector containing the grey values 0...255. This produces a 3D image where for fixed x and y, the vector (y,x,:) contains many zeros and (for the one grey value
G
where the binary image contained a1
) it contains the valueG
. So now you only need to sum over this third dimension to get an x m
image.Update
To test that this works correctly, lets go the other way first:
is a random greyscale image. You can calculate the 256 binary matrices like this:
We can now apply the solution I gave above
and verify that I returns the original image:
which gives
1
(true) :-).Update 2
You now mention that your binary images are in a cell array, I assume
binimg{1:256}
, with each cell containing an n x m binary array. If you can it probably makes sense to change the code that produces this data to create the 3D binary array I use above - cells are mostly usefull if different cells contain data of different types, shapes or sizes.If there are good reasons to stick with a cell array, you can convert it to a 3D array using
with
n
andm
as used above. The inner reshape is not necessary if you already havesize(binimg)==[1 256]
. So to sum it up, you need to use your cell arraybinimg
to calculate the 3D matrix binaryimage, which you can then use to calculate thenewimage
that you are interested in using the code at the very beginning of my answer.Hope this helps...