Как найти 4 точки рядом с пересечением двух линий

Скажем, у меня есть некоторые растровые данные (в черном), по которым некоторые линии рисовались в векторном формате (зеленым). Строки примерно соответствуют форме битмап-данных. В некоторых местах линии пересекаются.

Итак, что я пытаюсь сделать, зная положение пересечения зеленых линий, как я могу найти положение A, B, C и D?

Ниже приведены примеры:

enter image description here

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

Ответ 1

Самый простой подход, о котором я могу думать, заключается в следующем:

  • Отфильтруйте изображение, чтобы удалить зеленую линию. Простым подходом было бы использовать некоторое истончение, которое заполняется цветом фона соседнего пикселя.

  • Теперь у вас должно быть изображение, состоящее только из черных (широких) линий и белого фона.

  • Отфильтруйте изображение снова с помощью алгоритма определения угла, например, детектор Харриса. Это даст вам четыре угла.

Примечания:

  • В зависимости от входных данных вы можете получить более четырех углов. В любом случае, это хорошая идея, чтобы убедиться, что четыре угла, которые вы извлекли, действительно являются возможными углами пересечения.

  • Опять же, это довольно грубый подход, но если входные данные чисты, как в ваших примерах, а расстояние между зелеными линиями и черными линиями не слишком велико, я думаю, что это может сработать.

Ответ 2

Я предполагаю, что вы знаете, как получить координаты (x,y) (зеленого) пересечения векторной линии, поэтому я не буду оставлять эту часть.

Начиная с пикселя, ближайшего к (x,y), постепенно выходите наружу в квадратную спираль (или какой-либо другой шаблон поиска по вашему вкусу) от пикселя до пикселя. На каждом шаге проверьте, находитесь ли вы на черном пикселе с одним и только одним белым соседом Мура. Если это так, то место, где черный пиксель и его белый сосед касаются (вероятно, общий угол), являются одной из ваших точек (назовите это A). Продолжайте движение, пока не найдете еще три (B, C, D). Это будут четыре таких точки, ближайших к зеленому перекрестку, которые будут хорошо работать в четырех примерах, которые вы видите в своем вопросе.

Однако этот алгоритм потерпит неудачу, если зеленое пересечение будет наполовину между двумя черными пересечениями; в этом случае он будет смешивать точки с обоих черных пересечений. Если вы беспокоитесь об этом, то, как только вы найдете точку A, повторите инициализацию своей маршевой спирали, сосредоточив ее на A на этот раз, и пойдите, пока не найдете B, C, D. Это будет фактически "привязать" к ближайшему черному перекрестку.

Вы можете добавить больше соображений, чтобы избежать поиска в одной и той же области дважды; повторно инициировать или повторно сфокусировать свой шаблон поиска, как только вы найдете B, и еще раз, как только вы найдете C и т.д. Зависит от того, насколько вы хотите/должны получить.

Ответ 3

Во-первых, позвольте мне сказать, что я ничего не знаю о предмете, и у меня не было опыта с ним. Так что это только моя догадка. Но я бы начал с игнорирования зеленых линий - что, кстати, также не похоже на строки.

Btw, нужно ли это делать с дороги?

Итак, выключите зеленые линии. После этого возьмите маленький квадрат, как и любой из 4 из вышеперечисленных, который вы получили, пока не пройдете через все их, и найдите те, которые имеют максимальное соотношение черно-белых пикселей. Это должны быть те, у кого "перекресток". Путем сопоставления этих черных пикселей, которые граничат с белыми пикселями, вы должны иметь границы дороги/поля. После этого определение этих точек должно быть непростым.

Как я уже сказал, дикая догадка. Интересная проблема - задайтесь вопросом, что придумают знающие люди.

Ответ 4

Сначала вам нужно извлечь края из исходного изображения, чтобы получить полигоны, которые описывают черно-белую границу.

Затем вы перебираете точки ребер и вычисляете поточечное расстояние до точки пересечения двух зеленых линий. Четыре наименьших расстояния исходят от тех точек, которые вы ищете.

Это ответ на ваш вопрос? Или я что-то не понял?

Если вам нужны только 4 угла, вам не нужна зеленая линия: просто возьмите границы от извлечения края, затем сгладьте фильтр Savitzky-Golay и вычислите поточечную кривизну. Просто извлеките точки с максимальной кривизной.

Ответ 5

Вам нужна векторизация двоичного изображения. Наш университетский проект был прав на эту тему - Панель инструментов Corners, разрешающая обработку двоичных изображений в сжатой форме (не путайте заголовок - "сжатый" здесь означает, что двоичное изображение сначала преобразуется в связанные списки так называемых углов).

1) преобразуйте изображение в углы (см. главу 4 указанной выше ссылки). Затем вы можете использовать линейную интерполяцию угловых точек (глава 5.5) - вы изменили бы наш алгоритм, чтобы увидеть большие изменения наклона (~ 90 градусов) в больших частях линий.

2) вам не нужна зеленая линия. Вы можете использовать алгоритм скелетонизации, чтобы найти скелет черной части (см. Главу 5.4) и интерполировать этот скелет с линиями (см. Главу 5.5 вышеприведенной ссылки).

Если вас интересует проект, я могу спросить коллег, можем ли мы предоставить исходный код.

Ответ 6

Самый простой способ - скелетонирование. Сначала выделите зеленое и черно-белое изображение. Запустите алгоритм скелета (довольно простая морфологическая операция, также в OpenCV) на обоих изображениях и определите точки пересечения (это можно сделать с помощью простого 8-пиксельного подсчета пикселей в изображениях скелета: то есть для каждого черного пикселя подсчитывают, сколько пиксели соединяются по горизонтали, по вертикали или по диагонали, и если это значение > 4, это пересечение). Теперь выполните сопоставление ближайшего соседа для этих скелетонированных точек, и все готово.

Ответ 7

Вы должны уметь находить точку, где пересекаются зеленые линии, а также средняя точка, где черные линии пересекаются процессом эрозии (сжимаются до точек). Затем используйте ближайшую пару точек типа алгоритма, чтобы найти, какие черные линии пересекаются. Ближайшее пересечение зеленой линии тоже.

Затем вы можете выполнить поиск вдали от точки пересечения черных линий. Вам понадобится очередь приоритетов, которая будет обрабатывать точки в соответствии с их расстоянием от точки пересечения черных линий, ближайшей первой. Поместите четыре соседних точки в пересечение черных линий в очереди. Для каждой точки очереди вам нужно проверить, является ли это белым пикселем (мы хотим, чтобы это было), убедитесь, что он ранее не был посещен (пропустите в этом случае), а затем добавьте четыре соседних пикселя в очередь. Первые четыре белых пикселя должны быть теми, которые вы хотите (при условии, что у вас был хороший метод скелетонирования/сокращения для нахождения пересечения), но вы должны действительно брать белые пиксели, пока не получите первые четыре найденных, которые не смежны друг с другом.