Spaces:
Runtime error
Runtime error
| # Model card — modality classifier | |
| **Model.** EfficientNet-B0 (timm, ImageNet init, standard 3-channel stem; grayscale | |
| inputs replicated 1→3ch in the transform), 3-class head: `ct` / `mri` / `xray`. | |
| Weights: `backend/weights/modality_efficientnet_b0.pt` + `modality_config.json` | |
| (classes, input size, normalization, fitted temperature). Served by | |
| `backend/app/ml/imaging/real.py` under `MODEL_BACKEND=real`. | |
| ## Intended use | |
| Routing and cross-checking only: classify the modality of a claimant-uploaded | |
| medical image so the diagnostic-report draft addresses the right study type, and | |
| flag disagreement with the DICOM Modality tag as a fraud signal. The confidence | |
| that gates mandatory human review is the temperature-scaled probability. | |
| **Not** a diagnostic device. No clinical claim is made or implied; every output | |
| is reviewed by an imaging specialist before anything downstream happens. | |
| ## Training data | |
| 15,000 images from ROCOv2 (`eltorio/ROCOv2-radiology`), 5,000 per class, labels | |
| derived from UMLS CUI tags; only rows matching exactly one modality CUI are kept | |
| (`ml_training/datasets/build_datasets.py`). Single-source by design: drawing all | |
| three classes from one corpus avoids the per-class source confound (resolution, | |
| scanner, compression signatures) that turns stitched-together datasets into | |
| accidental source detectors. Train recipe adds random JPEG-quality re-encoding | |
| (q 60–95) and occasional Gaussian blur on top of geometric augs to kill the | |
| remaining compression/sharpness shortcuts. Split 80/10/10, seed 42. | |
| ## Metrics (held-out test split) | |
| | Metric | Value | | |
| |---|---| | |
| | Accuracy | 0.942 (n=1,543) | | |
| | Macro-F1 | 0.943 | | |
| | Per-class precision/recall | ct 0.92/0.93 · mri 0.91/0.92 · xray 1.00/0.98 | | |
| | ECE before → after temperature scaling | 0.030 → 0.016 | | |
| | Fitted temperature | 1.90 | | |
| Most confusion is ct↔mri (76 of the 90 errors); xray is near-perfect. Trained | |
| 2026-06-10, 12 epochs, seed 42, best epoch selected by val macro-F1 (0.938 at | |
| epoch 8). | |
| Reproduce: `uv run python -m ml_training.evaluate --weights-dir weights/ | |
| --data-dir ml_training/data --report` (full report at | |
| `ml_training/data/eval_report.json`, not committed). | |
| ## Caveats and limitations | |
| - **Domain shift is unmeasured.** ROCOv2 is publication-figure radiology; real | |
| claimant uploads (phone photos of films, portal exports, cropped screenshots) | |
| look different. The confound-killer augs narrow this gap but do not close it. | |
| - Three classes only; ultrasound, PET, mammography and anything else will be | |
| forced into the nearest of ct/mri/xray — the calibrated confidence (and the | |
| mandatory-review gate it feeds) is the only guardrail. | |
| - Calibration was fitted on the validation split of the same corpus; the | |
| temperature is not guaranteed to transfer under domain shift. | |
| - CUI-derived labels are weak labels; ROCOv2 label noise propagates. | |