Средний цвет для каждого суперпикселя в изображении в цветовом пространстве CIELAB - PullRequest
0 голосов
/ 02 марта 2019

Согласно справке MATLAB по измерению среднего цвета для каждого суперпикселя, я сегментирую изображение до 200 суперпикселей, и я попытался установить цвет каждого пикселя в выходном изображении на средний цвет CIELAB области суперпикселя.Входное изображение показано ниже:

The input image

B=imread('H.jpg');
A=rgb2lab(B);    // conversion from rgb to lab

output of command of imshow(A,[])

[L,N] = superpixels(A,200);
figure
BW = boundarymask(L);
imshow(imoverlay(A,BW,'cyan'),'InitialMagnification',67);


outputImage = zeros(size(A),'like',A);
idx = label2idx(L);
numRows = size(A,1);
numCols = size(A,2);
for labelVal = 1:N
  redIdx = idx{labelVal};
  greenIdx = idx{labelVal}+numRows*numCols;
  blueIdx = idx{labelVal}+2*numRows*numCols;
  outputImage(redIdx) = mean(A(redIdx));
  outputImage(greenIdx) = mean(A(greenIdx));
  outputImage(blueIdx) = mean(A(blueIdx));
end    
figure
imshow(outputImage,'InitialMagnification',67);

segmented image in the CIELAB color space

mean color of each superpixel in the CIELAB color space

Я не уверен, что вывод этого кода дает мне правильный средний цвет каждого суперпикселя в цветовом пространстве CIELAB.Имеет ли изображение такой другой цвет по сравнению с цветовым пространством RGB или код неправильный?Есть ли проблема в коде при измерении среднего цвета каналов цветового пространства CIELAB?

Ответы [ 2 ]

0 голосов
/ 03 марта 2019

Обратите внимание, что, хотя алгоритм суперпикселей, SLIC, работает в пространстве L * a * b *, он ожидает изображение RGB в качестве входных данных.Если вы хотите предварительно вычислить представление L * a * b * для последующего использования, как в вашем случае использования, вам необходимо использовать имя / значение IsInputLab.В противном случае алгоритм попытается преобразовать уже L * a * b * изображение в L * a * b *.

Вы хотите:

B=imread('H.jpg');
A=rgb2lab(B);  
[L,N] = superpixels(A, 200,'IsInputLab',true);

Крис Луено уже ответилсреднее вычисление признаков в суперпиксельном графе.Расстояние между суперпикселями аналогично, где вы по существу вычисляете объекты центроида для каждого суперпикселя, чтобы описать их положение, а затем измеряете расстояние между ними.Обратите внимание, что в приведенном ниже коде матрица симметрична относительно своей диагонали и 0 на диагонали.Я оставлю это вам, чтобы сделать это более эффективным, если вы заботитесь об этом.

distanceMatrix = zeros(N,N);
for m = 1:N
    for n = 1:n
        [i1,j1] = ind2sub(size(A),idx{m});
        [i1,j2] = ind2sub(size(A),idx{n});
        Icenter1 = mean(i1);
        Jcenter1 = mean(j1);
        Icenter2 = mean(i2);
        Jcenter2 = mean(j2);
        distanceMatrix(m,n) = sqrt((Icenter1-Icenter2)^2+(Jcenter1-Jcenter2)^2);
    end 
end
0 голосов
/ 02 марта 2019

Основная проблема здесь в том, что imshow показывает, что это не то, что содержат данные.

imshow предполагает, что для double входных значений значения пикселей находятся в диапазоне [0,1].Лаборатория имеет диапазон [0,100] в первом канале, и я полагаю, что он равен [-20,20] в двух других каналах (возможно, он отличается, но эти два канала симметричны относительно 0, что серо).

Если вы сделаете imshow(A,[]), то данные будут масштабированы, чтобы показать вам все.Таким образом, все каналы будут масштабироваться одинаково, поэтому это не лучший способ просмотра ваших данных, но в любом случае L-канал будет показан красным, а каналы a и b - зеленым и синим.Не ожидайте, что это будет выглядеть как ваше исходное изображение, хотя у вас все еще есть все данные для восстановления исходного изображения.

Далее, superpixels ожидает, что в качестве входных данных будет RGB-изображение, рассмотримпередавая исходное изображение B, а не лабораторное изображение A.Это не помешает вам использовать вычислительные средства каналов Lab в найденных суперпикселях. ( получается есть возможность использовать входное изображение Lab).

Если вы хотитечтобы измерить средние значения Lab внутри каждого суперпикселя и использовать их при дальнейшей обработке, не создавайте outputImage, а скорее таблицу с такими значениями:

data = zeros(N,3);
for labelVal = 1:N
  redIdx = idx{labelVal};
  greenIdx = idx{labelVal}+numRows*numCols;
  blueIdx = idx{labelVal}+2*numRows*numCols;
  data(labelVal,1) = mean(A(redIdx));
  data(labelVal,2) = mean(A(greenIdx));
  data(labelVal,3) = mean(A(blueIdx));
end    

Теперь, data(ii,:) - это Labзначения для числа суперпикселей ii.L==ii - это пиксели, принадлежащие этому суперпикселю.

...