Итак, я пытаюсь написать алгоритм маркировки подключенных компонентов, но это не дает мне желаемого результата. Прямо сейчас у меня есть изображение с тремя розами (которые не перекрываются), и я хочу отметить каждую розу своим собственным значением серого. Прежде чем применить алгоритм маркировки, я использую порог, чтобы избавиться от фона и сохранить только розы. Розы получают серое значение 1 (которое полностью белое), а фон получает серое значение 0 (что является черным). Вот изображение того, как это выглядит: Проблемы с алгоритмом маркировки подключенных компонентов
После этого я применяю алгоритм маркировки. Это должно дать розам три разных значения серого в соответствии с меткой, которую они дали. Но вместо этого алгоритм создает этот странный вид градиентного рисунка над первыми двумя розами, тогда как последний кажется единственным серым значением. Вот изображение:
Алгоритм может выглядеть сложным, но на самом деле это очень просто. Я сначала обрабатываю столбцы, а затем строки и для каждого нефонического пикселя. Я проверяю, отмечен ли какой-либо из его соседей (это означает, что их значение objectArray не равно нулю). Если это так, я добавляю их в список соседей. Затем я перехожу к проверке, не является ли этот список пустым, поэтому я однозначно маркирую текущий пиксель, увеличивая значение объектов и присваивая его значение текущему значению метки пикселя, и также устанавливаю родительское значение текущего пикселя на эту уникальную метку. Если он не пуст, я определяю наименьшее значение метки в списке соседей, задаю все родительские значения соседей этому значению метки, и я установил текущее значение метки и родительские значения этого ярлыка. Я повторяю это для каждого пикселя, пока не будет помечено все изображение.
Как только это будет сделано, я снова вернусь к значениям пикселей, на этот раз, чтобы установить значение метки каждого пикселя в его родительское значение. Затем я перехожу к присвоению пикселю нового значения серого в зависимости от его значения метки.
Я не понимаю, почему алгоритм не правильно маркирует розы. Кто-нибудь может мне помочь? Вот алгоритм:
public void label()
{
int objects = 1;
int[,] objectArray = new int[colors.GetLength(1), colors.GetLength(0)];
DisjointSets disjointSet = new DisjointSets();
int[,] parents = new int[colors.GetLength(1), colors.GetLength(0)];
List<List<int>> eqSet = new List<List<int>>();
for (int i = 0; i < colors.GetLength(1); i++) for (int j = 0; j < colors.GetLength(0); j++)
{
if (this[i, j].Gray == 1)
{
List<Label> neighbors = new List<Label>();
if (i > 0)
{
if (this[i - 1, j].Gray == 1)
{
if (objectArray[i - 1, j] != 0)
{
neighbors.Add(new Label(i - 1, j, 0));
}
}
if (j > 0)
{
if (this[i - 1, j - 1].Gray == 1)
{
if (objectArray[i - 1, j - 1] != 0)
{
neighbors.Add(new Label(i - 1, j - 1, 0));
}
}
}
if (j < colors.GetLength(0))
{
if (this[i - 1, j + 1].Gray == 1)
{
if (objectArray[i - 1, j] != 0)
{
neighbors.Add(new Label(i - 1, j, 0));
}
}
}
}
if (j > 0)
{
if (this[i, j - 1].Gray == 1)
{
if (objectArray[i, j - 1] != 0)
{
neighbors.Add(new Label(i, j - 1, 0));
}
}
if (i < colors.GetLength(1))
{
if (this[i + 1, j - 1].Gray == 1)
{
if (objectArray[i + 1, j - 1] != 0)
{
neighbors.Add(new Label(i + 1, j - 1, 0));
}
}
}
}
if (i < colors.GetLength(1))
{
if (this[i + 1, j].Gray == 1)
{
if (objectArray[i + 1, j] != 0)
{
neighbors.Add(new Label(i + 1, j, 0));
}
}
if (this[i + 1, j + 1].Gray == 1)
{
if (objectArray[i + 1, j + 1] != 0)
{
neighbors.Add(new Label(i + 1, j + 1, 0));
}
}
}
if (j < colors.GetLength(0))
{
if (this[i, j + 1].Gray == 1)
{
if (objectArray[i, j + 1] != 0)
{
neighbors.Add(new Label(i, j + 1, 0));
}
}
}
if (neighbors.Count == 0)
{
objects++;
objectArray[i, j] = objects;
parents[i, j] = objects;
}
if (neighbors.Count > 0)
{
int smallestLabel = 10000;
foreach (Label x in neighbors)
if (objectArray[x.X, x.Y] < smallestLabel)
smallestLabel = objectArray[x.X, x.Y];
foreach (Label x in neighbors)
parents[x.X, x.Y] = smallestLabel;
objectArray[i, j] = smallestLabel;
parents[i, j] = smallestLabel;
}
}
}
for (int i = 0; i < colors.GetLength(1); i++) for (int j = 0; j < colors.GetLength(0); j++)
{
if (this[i, j].Gray == 1)
{
if (objectArray[i, j] != 0)
{
objectArray[i, j] = parents[i, j];
ColorWrap c = this[i, j];
c.X = (float)objectArray[i, j]/objects;
c.Y = (float)objectArray[i, j]/objects;
c.Z = (float)objectArray[i, j]/objects;
this[i, j] = c;
}
}
}
}
Что такое «Этикетка»? –
Просто значение int для каждого пикселя, которое составляет объект, который я использую, чтобы дать этим объектам определенное значение серого. Алгоритм должен проверять изображение для подключенных пикселей и давать каждому найденному «объекту» («группе» подключенных пикселей, которые должны быть каждой из роз), значение метки (например, пиксели, составляющие верхнюю левую розу, будут получите значение метки 1, нижние левые пиксели будут получать значение метки 2, а пиксели, составляющие правую розу, получат значение метки 3). Я использую эти значения меток, чтобы дать этим пикселям новое значение серого (c.X = (float) objectArray [i, j]/objects; и т. Д.) – user1683526
@ user1683526 - это бинарное изображение или шкала серого? –