RGB histogram using bitshift in matlab

I'm trying to create a mozaic image in Matlab. The database consists of mostly RGB images but also some gray scale images.
I need to calculate the histograms - like in the example of the Wikipedia article about color histograms - for the RGB images and thought about using the bitshift operator in Matlab to combine the R,G and B channels.
nbins = 4;
nbits = 8;
index = bitshift(bitshift(image(:,:,1), log2(nbins)-nbits), 2*log2(nbins)) + ...
+ bitshift(bitshift(image(:,:,2), log2(nbins)-nbits), log2(nbins)) + ...
+ bitshift(image(:,:,3), log2(nbins)-nbits) + 1;
index is now a matrix of the same size as image with the index to the corresponding bin for the pixel value.
How can I sum the occurences of all unique values in this matrix to get the histogram of the RGB image?
I want for example the 4x4x4 histogram of each image. The histogram would then be a vector of size 1x64.
Is there a better approach than bitshift to calculate the histogram of an RGB image?

 Respuesta aceptada

Jonas
Jonas el 8 de Jun. de 2014

0 votos

The problem was solved by using the accumarray() function in matlab. First I had to reshape the index matrix into a column vector and then sum all elements with weight of one using accumarray. In that way I received the histogram of the RGB image.
The full answer to my question can be read in this question on StackOverflow

1 comentario

Image Analyst
Image Analyst el 8 de Jun. de 2014
Wow. Looks really complicated. And I can't tell if you get separate histograms or one histogram for the entire image regardless of color channels (which would be not very useful). Do you have a screenshot of your final histogram(s) that you can share so we can tell what you wanted?

Iniciar sesión para comentar.

Más respuestas (1)

Image Analyst
Image Analyst el 7 de Jun. de 2014

0 votos

Wow, what a horrible article in Wikipedia on color histograms. for crying out loud, they don't even show a single histogram! Anyway, I have no idea what you want. I don't know why you want the histogram to be an image the same as the image you're taking the histogram of. Can you give a screenshot? I don't know why bitshift would be needed.
To get a mosaic of images you can use montage() though if you have more than a few, you will run out of memory because it essentially stitched the images together at full resolution.
I attach my RGB histogram demo, for what it's worth.

7 comentarios

Jonas
Jonas el 7 de Jun. de 2014
I don't want the histogram to be the same size as the input image!
I want the color histogram for each image in the database to compare with the color histogram of a part of my query image.
I don't want to compare each color channel. I want to compare histograms with all channels combined. That's why I use bitshift.
Is there a better way? How may I combine the histograms for each channel if I use such approach?
Image Analyst
Image Analyst el 7 de Jun. de 2014
Have you run the demo I gave you yet? What's wrong with that?
Jonas
Jonas el 7 de Jun. de 2014
I thought it would be more efficient to compare 64 bin histograms instead of three 4 bin histograms.
How would I combine the three color histograms to get the most similar image? Sum the differences in mean values?
Image Analyst
Image Analyst el 7 de Jun. de 2014
The demo creates 3 256-bin histograms, not 3 4-bin histograms.
What does "combine the three color histograms to get the most similar image" mean? Do you mean something like this fun web site: http://www.npr.org/blogs/thetwo-way/2010/12/10/131960390/color-picker-sorts-flickr-photos-for-fun
Jonas
Jonas el 7 de Jun. de 2014
I know. 3 4-bin histograms was just an example, as in my original question.
Yeah, like that web site.
We have a query image separated into sub-images. Each sub-image should be replaced by an image from our database based on the sub-image's color.
What is the "subimage"? Do you mean one color channel of the RGB image? Or some cropped portion of a larger image?
Certainly one simplistic way to get started is to just compute the mean of each color channel for all test and database images.
% Extract the individual red, green, and blue color channels.
redChannel = rgbImage(:, :, 1);
greenChannel = rgbImage(:, :, 2);
blueChannel = rgbImage(:, :, 3);
redMean = mean2(redChannel);
greenMean = mean2(greenChannel);
blueMean = mean2(blueChannel);
You'd be better off converting the mean RGBs into LAB color space and compute the delta E (color difference in 3-dimensional color space). The database image with the lowest delta E from your image is the closest in color space to your test image.
colorSpaceTransform = makecform('srgb2lab');
lab_meansTest = applycform([redMean, greenMean, blueMean], colorSpaceTransform);
% Do above for all the DB images and the test image(s).
deltaL = lab_meansTest(1) - lab_meansDB(1);
deltaA = lab_meansTest(2) - lab_meansDB(2);
deltaB = lab_meansTest(3) - lab_meansDB(3);
deltaE = sqrt(deltaL^2 + deltaA^2 + deltaB^2);
Jonas
Jonas el 8 de Jun. de 2014
The subimage is a part (say 20x20 pixel large part) of the original RGB image. So the subimage is a RGB image.
Solved the problem with help from StackOverflow.

Iniciar sesión para comentar.

Preguntada:

el 7 de Jun. de 2014

Comentada:

el 8 de Jun. de 2014

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by