Pull to refresh

Детектирование округлостей на изображении (на примере микрофотографий)

Reading time 3 min
Views 18K
Всем привет! По своей профессии (строго говоря- будущей профессии) я вообще-то химик. Относительно недавно появилась интересная работа и объявилась необходимость много работать с цифровым микроскопом, делать большое количество фотографий и определённым образом их обрабатывать. А именно: находить линейные размеры частиц (чаще круглой формы и изначально- на глаз) и скрупулёзно заносить их в лабораторный журнал.
Неудивительно, что после первой же сотни изображений я крепко задумался о хоть какой-нибудь автоматизации этого процесса, но была одна загвоздка: я прекрасно знал, что «объектно-ориентированное программирование — это очень хорошо», но… Но я на тот момент владел только школьным TurboPascal, университетским VB и быдлокодингом на PHP в процедурном варианте. Потыкавшись по форумам, и учтя факт, что за день я успеваю поработать как минимум на двух ОС (Mac/Windows/Ubuntu существуют в эйфорическом симбиозе), я особо не задумывался и решил писать на Java.
Опуская подробности примерно недельной, в свободное от работы время, долбёжки своей головы об объектно-ориентированную парадигму программирования и бессонных ночей с мыслями наподобие «да как же, блин, это работает», я постараюсь максимально вкратце рассказать о том простом и быстром «алгоритме», который у меня родился. Стоит сразу сказать, что он годится только для достаточно четких изображений.
А вот, кстати, и типичный представитель (вернее, его примерно десятая часть), которого нужно обработать:



Сразу видно, что объекты — это окружности, и первое, что приходит в голову (да-да, спасибо университету, даже химики знают что это такое, и это действительно сразу же приходит в голову) — преобразование Хафа. Но… Опять «но»: объекты могут наезжать друг на друга, а также быть совершенно непохожими на окружности. Справедливости ради скажу, что я пробовал сделать это с помощью преобразования Хафа и библиотеки OpenCV на Python (здоровский язык) под Ubuntu… Пространство Хафа в этом случае получается слишком неоднозначным (== однородным) и за окружности принимается куча свободного места вокруг. Даже после предварительно выделенных границ в GIMP и прочих разных приёмов.

В общем, я решил написать свой почти велосипед. Итак, во-первых, нам нужно выделить границы. Попробовав несколько методов (их вообще-то не густо, так что, возможно, я попробовал их все), наиболее приемлемый результат давал метод «Canny Edge Detector» (как по-русски я не знаю, не бейте), и результат после этого получился такой:



После некоторого времени творческих мук, я наконец-то осознал, что области интереса — замкнуты. Вот только как выяснить, что эти точки образуют замкнутую кривую, и эти — нет? На обдумывание этого вопроса я потратил много времени, строил какие-то нечеловеческие выкладки, пытаясь применить тот математический аппарат, которому меня не так давно научили (а он оказался вполне качественным). И однажды меня осенило… Заливка!!! Нужно посмотреть, как работает инструмент «заливка» в графических Open Sourse проектах!!! Так я для себя открыл алгоритм Breadth-first search. Позже я всё-таки воспользовался для этих целей готовым классом, найденным на просторах интернета.
Вот так выглядит изображение после заливки:



Да! Мы выделили все интересующие нас объекты! Но только внутри них находятся какие-то непонятные штрихи. Только я начал думать, как же решить этот вопрос, и тут (прямо в тот же день) мне очень вовремя попадается статья на Хабрахабре про математическую морфологию (которая сейчас недоступна обычному пользователю). Сказано, сделано!
Вот так выглядит теперь наше изображение (метод «erode», матрицу взял стандартную крестообразную 3х3):



Ура! Готово! Теперь нам нужно ещё раз воспользоваться BFS-алгоритмом, и найти координаты центров и крайних точек наших частиц.
Итого получили почти готовую для использования программу для автоматических записей в журнал :) Т.к. от микроскопа идёт обычный usb-шнур, то очень хочется сразу в программе видеть изображение с камеры, тут же фотографировать и распознавать. Но это уже предмет моих следующих бессонных ночей.
А вот и конечный результат (кликабельно):

— 22.02.2011, 22:05 — перенёс в блог «обработка изображений»
Tags:
Hubs:
+94
Comments 38
Comments Comments 38

Articles