В репозитории код решения второго соревнования курса MADE по компьютерному зрению.
На тренировочном датасете обучил FPN с EfficientNet-B3. Сделал инференс на этом же датасете и выкинул почти все картинки, на которых IoU меньше 0.5. На этих картинках неразмечена часть номеров или размечена совсем криво.
FPN с SE-ResNeXt50_32x4d backbone (с ним на валидации был более высокий IoU, чем с EfficientNet-B3). Обучал в fp16. Размер картинок 512x512. Размер батча 20. Выбирал лосс, запуская обучение на несколько эпох, и смотрел IoU на валидации. В итоге выбрал взвешенную сумму двух лоссов: 0.7 * BinaryFocalLoss + 0.3 * BinaryLovaszLoss.
Из полученных масок получил контуры, для них с помощью OpenCV нашел минимальный ограничивающий прямоугольник. Прямоугольники с площадью меньше 250 пикселей выкинул.
Дальше учимся классифицировать полные номерные знаки от неполных и другого мусора. Номера кропаем с тренировочного датасета и ресайзим до 320x64. Над частью номеров делаем такие аугментации, чтобы номер был неполным и/или повернутым и учимся их различать от номеров без аугментаций.
Много эксперементировал c CRNN. Лучше всего получалось, если после feature extractor'a делать как можно меньше преобразований перед подачей в реккурентную сеть. Еще неплохо получилось с bidirectional GRU сначала по высоте картинки, а потом с еще одним bidirectional GRU по ширине.
Наткнулся на статью про TransformerOCR. Написал свою реализацию. Оказалось, что работает чуть хуже, чем CRNN. Поэкспериментировал с архитектурой. В итоге получилась сеть с двумя трансформерами, берущими признаки с разных слоев feature extractor'a. Стало чуть лучше.
Эпичный полет на лидерборде с 3-го на 65-ое место. Скорее всего дело в сегментации, сеть на картинках более чем с 4 номерами часто пропускала номера.
Для себя сделал вывод, что нужно было делать TTA и инференс на нескольких размерах, а потом усреднять предсказания.