|
|
||
|---|---|---|
| assets | ||
| docs | ||
| labels | ||
| models | ||
| src | ||
| tests | ||
| .dockerignore | ||
| .gitignore | ||
| Dockerfile | ||
| Dockerfile_cuda | ||
| Jenkinsfile | ||
| QWEN.md | ||
| README.md | ||
| condition.txt | ||
| condition_doctor.txt | ||
| docker-compose.yml | ||
| requirements.txt | ||
| run.sh | ||
README.md
🦴 DXA Quality Assessment
Сервис автоматизированного контроля качества денситометрических исследований (DXA): принимает DICOM, определяет анатомическую область, оценивает, пригодно ли изображение для клинической интерпретации, и формирует структурированный отчёт.
Что делает решение
| Шаг | Реализация |
|---|---|
| Определение анатомической области | Ширина кадра (позвоночник / бедро) + голова области + геометрия яркой зоны |
| Бинарная оценка качества | ResNet18 (ImageNet) → линейная голова; порог подобран по F1 на валидации |
| Тип нарушения | Общая категория для снимков с нарушением; детальный тип требует разметки типов на уровне снимка |
| Отчёт | XLSX/CSV со столбцами из требований; опционально zip с визуализацией зоны интереса |
| API | FastAPI: анализ, детальный анализ, пакетная обработка, экспорт, DICOM SR (текст) |
| Веб-интерфейс | Загрузка DICOM, таблица результатов, панель деталей с визуализацией, панель «О модели» |
Установка и запуск
python3 -m venv venv && source venv/bin/activate
pip install -r requirements.txt
./run.sh label # разметить датасет по Excel
./run.sh rename # план приведения имён файлов
./run.sh train # обучить модель качества
./run.sh infer "dataset_hack/Для теста" results.xlsx # пакетная обработка
./run.sh serve # API и веб-интерфейс на :8000
./run.sh split && ./run.sh compare # сравнить варианты разметки
./run.sh test # тесты
Для инференса только на CPU (образ меньше, без CUDA-колёс):
pip install -r requirements.txt --extra-index-url https://download.pytorch.org/whl/cpu
Обучение и инференс можно вызывать напрямую:
python -m src.dxa.train --epochs 100 --output-dir models
python -m src.dxa.inference --input-path dataset_hack --output-path results.xlsx --zip-out masks.zip
После запуска сервера:
- Веб-интерфейс: http://localhost:8000
- Swagger UI: http://localhost:8000/docs
Docker
docker build -t dxa-quality .
docker run -v /path/to/data:/data -v /path/to/models:/app/models -p 8000:8000 dxa-quality
Чекпоинт в образ не копируется: он монтируется в /app/models, путь задаётся
переменной DXA_MODEL_PATH (по умолчанию /app/models/dxa_model.pth). Без
чекпоинта сервис всё равно поднимается — /api/v1/health сообщает
model_loaded: false, а анализ отвечает ошибкой Model not loaded вместо тихой
неверной оценки. Из сети ничего не скачивается. Сборка проверяет, что приложение
импортируется и что офлайн-ассеты фронтенда на месте.
Архитектура
Схема работающего пути в терминах решения:
DICOM ──▶ предобработка ──▶ ResNet18 (заморожен) ──▶ линейная голова ──▶ логит
│ │
│ └──▶ голова области (вспомогательная)
│
├──▶ геометрия яркой зоны: область, ROI, геометрия кадра
└──▶ эвристики: резкость, «плотные» включения
Ключевые решения и почему они такие:
-
Линейный зонд вместо полного fine-tune. Уникальных снимков в наборе ~250. Полный fine-tune ResNet18 переобучается за несколько эпох (train F1 → 1.0 при val AUC ≈ 0.5). Замороженный backbone + линейная голова удерживает val AUC ≈ 0.7–0.85. Режим
--head mlp --freeze-epochs 0оставлен для экспериментов на большем объёме данных. -
Метки на уровне снимка. Источник —
labels/labels_images.csv, построенный из экспертной таблицы командой./run.sh label(разбор — вassets/labeling.md): в таблице отмечены критерии качества по каждому исследованию, а каждая область встречается в нём ровно один раз, поэтому вердикт переносится на снимок однозначно. Такой разметки — 76 нарушений из 251 (30.3 %). Правило выбрано измерением: учёт ручных пометок из имён файлов дал худший результат на held-out наборе, поэтому в метках они не участвуют. Резервный режим--labels-csv ""берёт метку из суффикса_good/_badи оставлен для совместимости. -
Склейка побайтных дублей. В датасете 482 файла, но 251 уникальный снимок: один и тот же кадр сохранён многократно под разными именами (часть — с меткой, часть — без). Без склейки одно изображение попадало бы в оба класса. Лишние байт-идентичные копии удалены.
-
Разбиение по исследованиям. Снимки одного исследования не попадают одновременно в train и val — иначе метрики завышаются за счёт утечки.
-
Аугментация отключена. Проверено экспериментально: яркостный разброс и сдвиг кадра снижают AUC с 0.87 до 0.56, потому что распределение яркости и положение области сами являются признаками качества. Флаг
--augmentвключает её для экспериментов. -
Порог по логиту. При доле нарушений ~15 % порог 0.5 даёт нулевой recall. Порог подбирается по F1 на валидации и сохраняется в чекпоинт; решение принимается по логиту (численно устойчиво при насыщении вероятностей).
Схемы системы
| Компоненты | Поток данных |
|---|---|
![]() |
![]() |
| Последовательность детального анализа | Развёртывание |
|---|---|
![]() |
![]() |
| Определение анатомической области | Основные сущности |
|---|---|
![]() |
![]() |
Схемы взяты из проектного документа и показывают целевую архитектуру: блоки
Orchestrator, UNet-сегментации и готовых вердиктов качества в решении не
реализованы. Работающий путь описан выше.
Формат выходных данных
Основные столбцы соответствуют требованиям задания:
| Столбец | Описание |
|---|---|
path_to_study |
Путь к исследованию (для HTTP-загрузки — upload://<имя>) |
study_uid |
StudyInstanceUID |
image_uid |
SOPInstanceUID |
anatomical_region |
spine / hip_left / hip_right / hip |
quality_class |
0 — качественное, 1 — есть нарушение |
violation_type |
Тип нарушения или пустая строка |
processing_status |
Success или Failure: <причина> |
time_of_processing |
Время обработки, секунды |
Дополнительно добавляются confidence, violation_reason, region_confidence
— они не мешают автоматическому разбору обязательных столбцов.
API
| Метод | Путь | Назначение |
|---|---|---|
| GET | / |
Веб-интерфейс |
| GET | /label |
Интерфейс ручной разметки: подтверждение и правка вердиктов специалистом |
| GET | /api/v1/health |
Статус, признак загрузки модели и её происхождение |
| GET | /api/v1/model |
Карточка решения: разметка, данные, метрики с интервалами, словарь нарушений |
| POST | /api/v1/analyze |
Базовый анализ одного файла |
| POST | /api/v1/analyze/detailed |
Расширенный отчёт, опционально маска |
| POST | /api/v1/analyze/sr |
Текстовое представление отчёта DICOM SR |
| POST | /api/v1/batch |
Пакетный анализ |
| POST | /api/v1/export |
Пакетный анализ и выгрузка в XLSX |
| GET | /api/v1/labeling/items |
Снимки датасета для разбора: текущая метка, её источник, расхождения |
| GET | /api/v1/labeling/image |
PNG снимка для просмотра |
| POST | /api/v1/labeling/verdict |
Сохранить вердикт специалиста |
| DELETE | /api/v1/labeling/verdict |
Снять вердикт, вернуть снимок к построенной разметке |
| GET | /api/v1/labeling/export |
Выгрузка разметки: scope=all принимается обучением как --labels-csv |
curl -X POST http://localhost:8000/api/v1/analyze -F "file=@study/spine.dcm"
{
"study_uid": "1.2.643...",
"image_uid": "1.2.643...",
"anatomical_region": "spine",
"quality_class": 1,
"quality_label": "Есть нарушение качества",
"violation_type": "artifact",
"violation_type_label": "Артефакты и импланты",
"violation_type_is_heuristic": true,
"violation_type_note": "Тип нарушения определён эвристикой по метрикам снимка, а не моделью...",
"reason": "Посторонние включения или артефакты в зоне интереса",
"confidence": 0.72,
"threshold_probability": 0.5103,
"processing_status": "Success"
}
Коды violation_type берутся из единого словаря src/dxa/violations.py
(positioning, axis_deviation, artifact, rotation, roi_incorrect,
motion, incomplete_anatomy, labeling_error, unspecified) — первые пять
кодирует экспертная таблица, остальные приходят из критериев пригодности. Поле
violation_type_is_heuristic показывает, что тип определён эвристикой, а не
моделью: модель решает только бинарную задачу. Подписи для интерфейса отдаёт
сервер, своей копии словаря фронтенд не держит.
Веб-интерфейс
Полоса состояния в шапке показывает, какая модель сейчас работает: имя чекпоинта, источник разметки, эпоху и порог. По интерфейсу сразу видно, какая версия решения отвечает, — без обращения к логам.
Строки таблицы результатов кликабельны, но об этом надо сказать прямо — иначе не догадываются. Над таблицей висит подсказка «Нажмите на любую строку», в конце каждой строки есть кнопка «Открыть», а клик по строке прокручивает страницу к панели деталей. Подсказка скрывается, когда фильтр не оставил ни одной строки. Кнопка «Открыть» — настоящая кнопка, поэтому панель доступна и с клавиатуры (Tab + Enter), а не только мышью. Сама таблица со статистикой и подсказкой — на первом скриншоте.
Панель деталей открывается по клику на строку: заключение, измерения и визуализация снимка. Специально показаны обе ветки — «нарушение» и «норма»:
![]() |
![]() |
| Нарушение. Бейдж «Нарушение», уровень HIGH, заключение с вероятностью и порогом, тип нарушения с пометкой «эвристика». | Норма. Зелёный бейдж. Измерения (резкость, границы области) подписаны как справочные — их пороги не калиброваны. |
Панель «О модели» (кнопка в шапке): что за чекпоинт работает, на какой разметке он обучен, с каким порогом решает, метрики сравнения с 95 % интервалами, состав данных, словарь типов нарушений и список ограничений.
Источник всех этих значений — сервер (/api/v1/health, /api/v1/model).
Фронтенд намеренно не держит собственных копий: раньше подписи типов нарушений
были продублированы в dxa-app.js и разошлись с серверными, из-за чего коды
экспертной таблицы показывались как есть.
Что интерфейс теперь не утверждает:
- тип нарушения помечен как «эвристика» с пояснением — модель решает только бинарную задачу и тип не предсказывает;
- метрика рабочего чекпоинта помечена как завышенная прямо в баннере состояния и в карточке: чекпоинт выбран лучшим из пяти seed'ов, честная оценка варианта — среднее по seed'ам;
- плитка «Ср. уверенность модели» больше не называется точностью: точность требует эталонных меток, которых для произвольного файла нет;
- числовые метрики в панели деталей по-прежнему идут под дисклеймером о некалиброванности порогов.
Ручная разметка (/label)
Поштучной экспертной оценки снимков в наборе нет: таблица оценивает исследование,
и снимок наследует вердикт исследования. Закрыть это автоматически нечем —
локальная vision-модель оказалась непригодна (assets/labeling.md §11). Поэтому
в сервисе есть отдельный интерфейс ручной разметки: раздел 2.6 задания просит
«автоматическую коррекцию разметки с возможностью подтверждения специалистом».
Откройте http://localhost:8000/label. Интерфейс показывает снимок целиком и его
текущую метку с указанием источника (экспертная таблица, имя файла, ручной вердикт). Снимки, где метка разметки расходится с пометкой в имени файла, идут
первыми: там ошибка возможна в любом из источников. Специалист подтверждает
вердикт или ставит свой — область, «годное / нарушение», тип нарушения,
комментарий.
Вердикты сохраняются в labels/manual_labels.csv в том же формате, что и
построенная разметка, поэтому файл можно сразу передать обучению:
curl -o manual_labels.csv "http://localhost:8000/api/v1/labeling/export?scope=all"
python -m src.dxa.train --labels-csv manual_labels.csv
scope=all накладывает ручные вердикты на построенную разметку (весь набор),
scope=reviewed отдаёт только разобранные снимки — для сверки с построенной
разметкой. Оценка модели в интерфейсе намеренно не показывается: подсказка
смещала бы разметчика, а ценность здесь именно в независимом суждении.
Передать разметку врачу: автономный HTML-пакет
Интерфейс /label требует запущенного сервиса, а размечать должен специалист — на
своей машине, без Python и без сети. Поэтому тот же сценарий упаковывается в один
файл: снимки встроены внутрь, вердикты хранятся в браузере, выгрузка — CSV.
./run.sh review --out review/doctor_review.html # весь набор, ~7 МБ
./run.sh review --limit 20 --out review/pilot.html # пилот на выборке из 20 снимков
Файл врач открывает двойным щелчком: снимок, построенная метка с указанием
источника, кнопки «годное / нарушение», тип нарушения, комментарий, горячие
клавиши. Работает полностью офлайн — страница не делает ни одного сетевого
запроса, и это проверяется автоматически (tests/browser/review_pack.js).
Прогресс сохраняется в браузере, а кнопка «Выгрузить CSV» отдаёт файл, который
принимается обучением как есть; загрузить его обратно можно на другой машине —
кнопкой «Загрузить CSV».
Вердикты врача накладываются на построенную разметку одной командой, с проверкой, что все пути есть в датасете:
./run.sh review --merge review/doctor.csv --out labels/labels_images_reviewed.csv
python -m src.dxa.train --labels-csv labels/labels_images_reviewed.csv
Каталог review/ в git не хранится: пакет генерируется, а внутри — медицинские
снимки.
Метрики
Метрики зависят от выбранного разбиения по исследованиям, поэтому приводятся с разбросом. Основная оценка — на фиксированном разбиении по исследованиям (обучение 198 снимков / 81 исследование, валидация 53 снимка / 19 исследований, 16 нарушений), пять seed'ов обучения, эталон — вердикт эксперта:
| Что измерено | Значение | Как измерено |
|---|---|---|
| ROC-AUC | 0.6726 [0.6367, 0.7086] | 5 seed'ов на фиксированном разбиении |
| PR-AUC | 0.4753 [0.4188, 0.5318] | там же; базовый уровень при 30 % нарушений — 0.30 |
| F1 | 0.5559 [0.5212, 0.5906] | там же; порог подобран на той же валидации — смещено вверх |
| ROC-AUC по областям | позвоночник 0.929, бедро R 0.606, бедро L 0.567 | рабочий чекпоинт, собственная валидация |
| Контрольная задача «позвоночник / бедро» | AUC 1.00 | проверка работоспособности пайплайна |
| Модель использует снимок, а не область | AUC 0.885 против 0.534 у правила области | discriminator на всём наборе, включая обучающие снимки |
Метрики по областям — в models/train_report.md, он создаётся при обучении.
Разбивка важна, потому что нарушения распределены неравномерно: в позвоночнике
33 из 99, у бёдер 20–22 из 73–78, а область почти однозначно определяется по
ширине кадра. Поэтому общий AUC частично отражает различение области, а не только
распознавание дефекта.
Выбор правила разметки
Метку можно было строить только из экспертной таблицы или дополнительно
учитывать пометки, проставленные вручную в именах файлов (суффикс _bad).
Пометки расходились с оценкой эксперта в 62 случаях из 251, поэтому правило
выбиралось измерением: одно разбиение, пять seed'ов, один эталон.
| Метрика (эталон) | только таблица | с суффиксами имён |
|---|---|---|
| ROC-AUC | 0.6726 [0.6367, 0.7086] | 0.6003 [0.5592, 0.6415] |
| PR-AUC | 0.4753 [0.4188, 0.5318] | 0.3864 [0.3487, 0.4242] |
| F1 | 0.5559 [0.5212, 0.5906] | 0.5354 [0.4978, 0.5729] |
| Recall / Precision | 0.713 / 0.472 | 0.788 / 0.409 |
Парная разница (только таблица − с суффиксами): ROC-AUC +0.0723
[+0.0541, +0.0905], PR-AUC +0.0889 [+0.0500, +0.1277] — знаки +++++, то
есть преимущество на всех пяти seed'ах.
Принято правило «только экспертная таблица». Пометки в именах файлов проставлялись вручную и оказались ненадёжными: они ухудшали согласие модели с экспертом на невиданных исследованиях. Оговорка: эталон — та же таблица, поэтому вариант, обучавшийся на ней, в выигрышном положении; значимо то, что добавление ненадёжных пометок согласие снижает.
Отчёт с полными числами и разбором ограничений — assets/labeling.md; отчёт
обучения рабочего чекпоинта — models/train_report.json. Само сравнение правил
хранится только в виде чисел в этих документах: чекпоинты прогонов удалены,
а пересобрать их можно командой ./run.sh split && ./run.sh compare.
Время обработки одного снимка — порядка 0.02–0.05 с на CPU (ResNet18 с замороженным backbone), то есть требование «не более 3 минут на исследование» выполняется с большим запасом.
Ограничения (важно для интерпретации)
-
Разметка выведена из оценки исследования. Экспертная таблица описывает исследование, а не снимок; перенос однозначен (область встречается один раз), но поштучной экспертной оценки снимков в наборе нет. Происхождение каждой строки зафиксировано в
labels/labels_images.csv. Для поштучной разметки есть интерфейс/label(см. «Веб-интерфейс»), им ещё не пользовались. Разбор — вassets/labeling.md. -
Мало данных. 251 уникальный снимок, 76 нарушений. Доверительные интервалы широкие; оценка на закрытом наборе может отличаться.
-
Тип нарушения определяется эвристиками, а не обученной моделью. Для честного мультикласса нужна разметка типов на уровне снимка — её даёт
/label. -
Область определяется по размеру кадра. Признак безошибочно работает на этом оборудовании (99/99 для позвоночника), но при смене аппарата порог
SPINE_MIN_WIDTHпотребует калибровки. -
В DICOM нет разметки ROI. Ни overlay, ни graphic annotation в файлах нет, поэтому корректность нанесённых областей измерения нельзя проверить прямым сравнением — оценивается только геометрия видимой зоны.
-
Эвристики из
src/quality/detailed_assessment.pyне калиброваны. Пороги для «движения», «артефактов» и отступов ROI рассчитаны на другой масштаб интенсивностей: на этом наборе они срабатывают почти для любого снимка, а признак резкости ведёт себя противоположно в позвоночнике и бёдрах. Поэтому в панели деталей показываются числовые измерения с пометкой «справ.», а не вердикты «Да/Нет». Классификацию выполняет только модель. Проверить её вклад можно командой:python -m src.dxa.discriminator --model-path models/dxa_model.pth
Что проверено и как
| Проверка | Команда | Результат |
|---|---|---|
| Модель использует снимок, а не только область | python -m src.dxa.discriminator |
AUC 0.885 против 0.534 у правила «позвоночник = нарушение»; внутри областей у модели 0.88–0.95, у правила 0.50 |
| Контракт API для веб-интерфейса | python -m pytest tests/test_api_contract.py |
поля панели деталей, различимость метрик, PNG-визуализации, отсутствие некалиброванных вердиктов, канонические коды типов нарушений, карточка модели |
| Ручная разметка | python -m pytest tests/test_manual_labels.py tests/test_labeling_api.py |
проверка вердикта (область, метка, совместимость типа нарушения с областью), хранение и наложение на построенную разметку, отказ отдавать файлы вне датасета, выгрузка, читаемая обучением |
| Пакет разметки для врача | python -m pytest tests/test_review_pack.py |
отпечаток набора, порядок «расхождения первыми», встроенные данные, отсутствие сетевых ссылок в странице, слияние вердиктов с разметкой |
| Единый словарь нарушений | python -m pytest tests/test_violations.py |
коды, подписи, коды SR, приведение устаревших значений, согласованность с таблицей |
| Разметка и разбиение данных | python -m pytest tests/test_labels.py |
склейка дублей, разбор имён, фиксация разбиения, отсутствие утечки между train/val |
| Имена DICOM-файлов | python -m pytest tests/test_rename_files.py |
разбор имён, поиск свободного номера при конфликте, отказ от угадывания области, цикл «применить → откатить» |
| Разметка по экспертной таблице | python -m pytest tests/test_excel_labels.py |
чтение критериев, голосование по области, перенос на единственное бедро, правила table/union/expert, подключение к обучению |
| Выбор правила метки | ./run.sh split && ./run.sh compare |
ROC-AUC 0.6726 против 0.6003 по эталону, парная Δ +0.0723 [+0.0541, +0.0905], 5/5 seed'ов в пользу экспертной таблицы |
| Метрики и порог | python -m pytest tests/test_preprocess_and_model.py |
подбор порога при дисбалансе, roundtrip чекпоинта, BatchNorm |
| Веб-интерфейс в браузере | node tests/browser/ui_check.js |
подсказка о кликабельности строк видна и скрывается на пустом фильтре; кнопка «Открыть» открывает панель; значения панели меняются при переключении строк; панель «О модели» наполняется метриками и словарём |
| Интерфейс ручной разметки в браузере | node tests/browser/ui_labeling.js |
расхождения идут первыми, снимок отрисовывается, вердикт сохраняется и переживает перезагрузку страницы, фильтр «только расхождения» работает, внешних запросов нет |
| Работа без сети | node tests/browser/ui_offline.js |
ноль внешних запросов, стили и иконки на месте |
Браузерные проверки требуют запущенного сервера:
python -m uvicorn src.main:app --port 8123
node tests/browser/ui_check.js # панель деталей обновляется по клику
node tests/browser/ui_offline.js # работа без доступа к внешним сервисам
# проверка ручной разметки пишет вердикты, поэтому файл стоит отвести в /tmp:
DXA_MANUAL_LABELS=/tmp/manual_ui.csv python -m uvicorn src.main:app --port 8123
node tests/browser/ui_labeling.js
Офлайн-режим обеспечен локальными копиями Tailwind и FontAwesome
(src/api/static/vendor, src/api/static/webfonts); страница не обращается к CDN.
План доработки
- Разметить типы нарушений на уровне снимка и обучить мультилейбл-классификатор.
- Собрать 500+ исследований для устойчивых метрик и честной валидации.
- Заменить порог по ширине кадра на калибровку по метаданным аппарата.
Структура проекта
bone_2026/
├── src/
│ ├── main.py # FastAPI: маршруты и загрузка модели
│ ├── dxa/ # действующий модуль оценки качества
│ │ ├── labels.py # разбор имён, метки, склейка дублей, сплит
│ │ ├── excel_labels.py # разметка снимков по экспертной таблице
│ │ ├── manual_labels.py # ручная разметка: хранение вердиктов (/label)
│ │ ├── review_pack.py # автономный HTML-пакет разметки для врача
│ │ ├── rename_files.py # приведение имён DICOM к единому виду
│ │ ├── violations.py # единый словарь типов нарушений (коды, подписи)
│ │ ├── model_card.py # карточка решения для /api/v1/model и интерфейса
│ │ ├── compare_labels.py # сравнение источников разметки на одном наборе
│ │ ├── discriminator.py # проверка вклада содержимого снимка
│ │ ├── render.py # рендер снимков и контактных листов
│ │ ├── preprocess.py # DICOM -> тензор (общий для обучения и API)
│ │ ├── dataset.py # Dataset и DataLoader
│ │ ├── model.py # сеть, метрики, подбор порога
│ │ ├── train.py # обучение и отчёт
│ │ └── inference.py # пакетный инференс, определение области
│ ├── quality/ # эвристики качества, используются API
│ └── api/static/ # веб-интерфейс (index.html — анализ, label.html — разметка)
├── labels/labels_images.csv # разметка снимков: официальная (+ .xlsx)
├── labels/manual_labels.csv # вердикты специалиста из /label (появляется после правок)
├── labels/labels_images_table.csv # вариант «только таблица» (то же, что выше)
├── labels/labels_images_union.csv # вариант «таблица или суффикс имени»
├── labels/labels_images_expert.csv # эталон для оценки: только снимки с оценкой
├── labels/split_expert_seed42.json # зафиксированное разбиение (19 исследований)
├── labels/rename_map.csv # карта переименований файлов (для отката)
├── assets/img/ # схемы архитектуры и скриншоты интерфейса
├── assets/labeling.md # как построена разметка и как сравнивались варианты
├── models/dxa_model.pth # рабочий чекпоинт (+ train_report.md/.json)
├── tests/ # pytest: метки, сплит, метрики, модель, API
├── dataset_hack/ # данные (в git не хранятся)
├── Dockerfile
├── requirements.txt
└── run.sh
Запуск обучения
python -m src.dxa.train --epochs 100 --output-dir models
| Параметр | По умолчанию | Описание |
|---|---|---|
--data-root |
dataset_hack |
Каталог датасета |
--annotation-path |
dataset_hack/НД_для_обучения/разметка.xlsx |
Excel с разметкой (только отчёт о расхождениях) |
--labels-csv |
labels/labels_images.csv |
Разметка снимков из ./run.sh label; пустая строка — метки из имён файлов; отсутствующий файл — откат к именам с предупреждением |
--split-file |
— | Зафиксированное разбиение из ./run.sh split; одинаковый held-out набор для сравнения вариантов разметки |
--backbone |
resnet18 |
resnet18 / resnet34 |
--head |
linear |
linear (линейный зонд) / mlp |
--freeze-epochs |
-1 |
-1 — backbone заморожен всегда; 0 — обучать всю сеть |
--epochs, --batch-size, --learning-rate, --weight-decay |
100 / 16 / 3e-4 / 5e-2 | Оптимизация |
--balance |
none |
loss / sampler для компенсации дисбаланса |
--val-fraction, --seed |
0.2 / 42 | Разбиение по исследованиям |
--augment |
выключено | Включает яркостную аугментацию (ухудшает метрики, см. п. 5) |
--output-dir |
models |
Куда сохранять чекпоинт и отчёты |
--dry-run |
— | Проверить разбор данных и разбиение без обучения |
После обучения в --output-dir появляются dxa_model.pth, train_report.md
и train_report.json; отчёт удобно приложить к презентации.
Команда
- Грачев Денис — разработка
- Грачев Татьяна — капитан







