Следующая новость
Предыдущая новость

YOLO! Используем нейросеть, чтобы следить за людьми и разгадывать капчу

14.04.2021 14:42
YOLO! Используем нейросеть, чтобы следить за людьми и разгадывать капчу

Содержание статьи

  • Какие бывают алгоритмы
  • Пишем код
  • Модифицируем приложение
  • Итоги

You only look once, или YOLO, — эффектив­ный алго­ритм, который поз­воля­ет выделять объ­екты на изоб­ражении. В этой статье мы исполь­зуем его, что­бы написать на Python прог­рамму для опре­деле­ния чис­ла людей в помеще­нии, а по дороге опро­буем его в раз­гадыва­нии кап­чи.

Ес­ли ты смот­рел «Тер­минатор», то пом­нишь кад­ры из глаз T-800: он смот­рел по сто­ронам и опре­делял раз­ные объ­екты. Тог­да о такой машине мож­но было толь­ко меч­тать, а сегод­ня ее мож­но смас­терить самому из готовых час­тей.

Кадр из филь­ма «Тер­минатор»

Рас­позна­вание объ­ектов сегод­ня при­гож­дает­ся для решения самых раз­ных задач: клас­сифика­ции видов рас­тений и живот­ных, рас­позна­вания лиц, опре­деле­ния габари­тов объ­ектов — и это далеко не пол­ный спи­сок.

Какие бывают алгоритмы

Су­щес­тву­ет нес­коль­ко алго­рит­мов обна­руже­ния объ­ектов на изоб­ражени­ях и видео. Пос­мотрим, что они собой пред­став­ляют.

R-CNN, Region-Based Convolutional Neural Network

Спер­ва на изоб­ражении с помощью алго­рит­ма выбороч­ного поис­ка выделя­ются реги­оны, которые пред­положи­тель­но содер­жат объ­ект. Далее свер­точная ней­рон­ная сеть (CNN) пыта­ется выявить приз­наки объ­ектов для каж­дого из этих реги­онов, пос­ле чего машина опор­ных век­торов клас­сифици­рует получен­ные дан­ные и сооб­щает класс обна­ружен­ного объ­екта.

Об­работ­ка в режиме реаль­ного вре­мени: не под­держи­вает­ся.

Fast R-CNN, Fast Region-Based Convolutional Neural Network

Под­ход ана­логи­чен алго­рит­му R-CNN. Но вмес­то того, что­бы пред­варитель­но выделять реги­оны, мы переда­ем вход­ное изоб­ражение в CNN для соз­дания свер­точной кар­ты приз­наков, где затем будет про­исхо­дить выбороч­ный поиск, а пред­ска­зание клас­са объ­ектов выпол­няет спе­циаль­ный слой Softmax.

Об­работ­ка в режиме реаль­ного вре­мени: не под­держи­вает­ся.

Faster R-CNN, Faster Region-Based Convolutional Neural Network

По­доб­но Fast R-CNN, изоб­ражение переда­ется в CNN соз­дания свер­точной кар­ты приз­наков, но вмес­то алго­рит­ма выбороч­ного поис­ка для прог­нозиро­вания пред­ложений по реги­онам исполь­зует­ся отдель­ная сеть.

Об­работ­ка в режиме реаль­ного вре­мени: под­держи­вает­ся при высоких вычис­литель­ных мощ­ностях.

YOLO, You Only Look Once

Изоб­ражение делит­ся на квад­ратную сет­ку. Для каж­дой ячей­ки сети CNN выводит веро­ятности опре­деля­емо­го клас­са. Ячей­ки, име­ющие веро­ятность клас­са выше порого­вого зна­чения, выбира­ются и исполь­зуют­ся для опре­деле­ния мес­тополо­жения объ­екта на изоб­ражении.

Об­работ­ка в режиме реаль­ного вре­мени: под­держи­вает­ся!

Как видишь, YOLO пока что луч­ший вари­ант для обна­руже­ния и рас­позна­вания обра­зов. Он отли­чает­ся высокой ско­ростью и точ­ностью обна­руже­ния объ­ектов, а еще этот алго­ритм мож­но исполь­зовать в про­ектах на Android и Raspberry Pi с помощью нет­ребова­тель­ного tiny-вари­анта сети, с которым мы с тобой сегод­ня будем работать.

Tiny-вари­ант нес­коль­ко про­игры­вает в точ­ности пол­ноцен­ному вари­анту сети, но и тре­бует мень­шей вычис­литель­ной мощ­ности, что поз­волит запус­тить про­ект, который мы сегод­ня будем делать, как на сла­бом компь­юте­ре, так и, при желании, на смар­тфо­не.

Пишем код

Что­бы написать лег­ковес­ное при­ложе­ние для обна­руже­ния объ­ектов на изоб­ражении, нам с тобой понадо­бят­ся:

  • наз­вания клас­сов датасе­та COCO, которые уме­ет опре­делять сеть YOLO;
  • кон­фигура­ции для tiny-вари­анта сети YOLO;
  • ве­са для tiny-вари­анта сети YOLO.

До­пол­нитель­но уста­новим биб­лиоте­ки OpenCV и NumPy:

pip install opencv-python pip install numpy

Те­перь напишем при­ложе­ние, которое будет находить объ­екты на изоб­ражении при помощи YOLO и отме­чать их.

Мы поп­робу­ем обой­ти CAPTCHA с изоб­ражени­ями гру­зови­ков — класс truck в датасе­те COCO. Допол­нитель­но мы пос­чита­ем количес­тво обна­ружен­ных объ­ектов нуж­ного нам клас­са и выведем всю информа­цию на экран.

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

import cv2import numpy as npdef apply_yolo_object_detection(image_to_process): """ Распознавание и определение координат объектов на изображении :param image_to_process: исходное изображение :return: изображение с размеченными объектами и подписями к ним """ height, width, depth = image_to_process.shape blob = cv2.dnn.blobFromImage(image_to_process, 1 / 255, (608, 608), (0, 0, 0), swapRB=True, crop=False) net.setInput(blob) outs = net.forward(out_layers) class_indexes, class_scores, boxes = ([] for i in range(3)) objects_count = 0 # Запуск поиска объектов на изображении for out in outs: for obj in out: scores = obj[5:] class_index = np.argmax(scores) class_score = scores[class_index] if class_score > 0: center_x = int(obj[0] * width) center_y = int(obj[1] * height) obj_width = int(obj[2] * width) obj_height = int(obj[3] * height) box = [center_x - obj_width // 2, center_y - obj_height // 2, obj_width, obj_height] boxes.append(box) class_indexes.append(class_index) class_scores.append(float(class_score)) # Выборка chosen_boxes = cv2.dnn.NMSBoxes(boxes, class_scores, 0.0, 0.4) for box_index in chosen_boxes: box_index = box_index[0] box = boxes[box_index] class_index = class_indexes[box_index] # Для отладки рисуем объекты, входящие в искомые классы if classes[class_index] in classes_to_look_for: objects_count += 1 image_to_process = draw_object_bounding_box(image_to_process, class_index, box) final_image = draw_object_count(image_to_process, objects_count) return final_image

Да­лее добавим фун­кцию, которая поз­волит нам обвести най­ден­ные на изоб­ражении объ­екты с помощью коор­динат гра­ниц, которые мы получи­ли в apply_yolo_object_detection.

def draw_object_bounding_box(image_to_process, index, box): """ Рисование границ объекта с подписями :param image_to_process: исходное изображение :param index: индекс определенного с помощью YOLO класса объекта :param box: координаты области вокруг объекта :return: изображение с отмеченными объектами """ x, y, w, h = box start = (x, y) end = (x + w, y + h) color = (0, 255, 0) width = 2 final_image = cv2.rectangle(image_to_process, start, end, color, width) start = (x, y - 10) font_size = 1 font = cv2.FONT_HERSHEY_SIMPLEX width = 2 text = classes[index] final_image = cv2.putText(final_image, text, start, font, font_size, color, width, cv2.LINE_AA) return final_image

Продолжение доступно только участникам

Материалы из последних выпусков становятся доступны по отдельности только через два месяца после публикации. Чтобы продолжить чтение, необходимо стать участником сообщества «Xakep.ru».

Присоединяйся к сообществу «Xakep.ru»!

Членство в сообществе в течение указанного срока откроет тебе доступ ко ВСЕМ материалам «Хакера», позволит скачивать выпуски в PDF, отключит рекламу на сайте и увеличит личную накопительную скидку! Подробнее

1 год

9300 р.

1 месяц

870 р.

Я уже участник «Xakep.ru»

Источник

Последние новости