Skip to content

Commit 33a0f16

Browse files
first version of new docs
1 parent 1479dfa commit 33a0f16

5 files changed

Lines changed: 409 additions & 26 deletions

File tree

README.md

Lines changed: 18 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
## Table of Contents
1010

1111
- [Overview](#overview)
12+
- [Documentation](#documentation)
1213
- [Repository Structure](#repository-structure)
1314
- [Getting Started](#getting-started)
1415
- [Data Format](#data-format)
@@ -40,6 +41,16 @@ All train subjects have CT labels. The 8 fully-equipped subjects additionally in
4041

4142
---
4243

44+
## 📚 Documentation
45+
46+
| Guide | Description |
47+
|-------|-------------|
48+
| [PET Background](docs/pet-background.md) | PET physics and attenuation correction — start here if you're new to PET |
49+
| [Submission Guide](docs/submission-guide.md) | Validation, dry-run, and final submission phases explained |
50+
| [Docker Packaging](docs/docker-packaging.md) | How to containerize your model, with baseline as a worked example |
51+
52+
---
53+
4354
## 📁 Repository Structure
4455

4556
```
@@ -202,35 +213,17 @@ python src/evaluation/eval.py <subject_dir> <pred_pet.nii.gz> <pred_ct.nii.gz> \
202213

203214
## 📬 Submission
204215

205-
Wrap your algorithm in a Docker container. The evaluation system will run your container with two mounts:
206-
207-
- `/data/features/` — read-only input directory (contents of `features/` for the subject)
208-
- `/data/output/` — write directory for your predictions
209-
210-
Your container must write the predicted CT to `/data/output/ct.nii.gz` as a NIfTI file in Hounsfield units (HU), with the same affine and shape as the input CT space.
211-
212-
The exact command used to run your container is:
213-
214-
```bash
215-
docker run --rm \
216-
--memory 128g \
217-
--network none \
218-
-v /path/to/sub-XXX/features:/data/features:ro \
219-
-v /path/to/output:/data/output \
220-
<your-image>
221-
```
216+
There are three submission phases — **Validation** (NIfTI upload to Codabench), **Dry Run** (container sanity check), and **Final Test** (container + full recon + evaluation). Validation and Dry Run run concurrently during the pre-evaluation period (May 15 – Jun 15).
222217

223-
**Constraints enforced at evaluation time:**
218+
See [docs/submission-guide.md](docs/submission-guide.md) for full instructions on each phase.
224219

225-
| Resource | Limit |
226-
|----------|-------|
227-
| RAM | 128 GB |
228-
| Wall-clock time | 5 minutes |
229-
| Network access | None (`--network none`) |
220+
For phases requiring a Docker container, your image must:
230221

231-
No other files or directories are mounted. Make sure all model weights and dependencies are baked into your image — no downloads at inference time.
222+
- Read from `/data/features/` (read-only mount)
223+
- Write `ct.nii.gz` to `/data/output/`
224+
- Run within 5 minutes, with 128 GB RAM and no network access
232225

233-
Submit your image name and tag via Codabench (see [website](https://bic-mac-challenge.github.io/) for registration and submission instructions).
226+
See [docs/docker-packaging.md](docs/docker-packaging.md) for a step-by-step guide to building and testing your container, with the baseline as a worked example.
234227

235228
---
236229

docs/docker-packaging.md

Lines changed: 72 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
# Docker Packaging Guide
2+
3+
Your container is run once per subject with two volume mounts:
4+
5+
```bash
6+
docker run --rm \
7+
--memory 128g \
8+
--network none \
9+
--gpus all \
10+
-v /path/to/subject/features:/data/features:ro \
11+
-v /path/to/output:/data/output \
12+
<your-image>
13+
```
14+
15+
| Mount | Mode | Contents |
16+
|-------|------|---------|
17+
| `/data/features/` | read-only | NAC-PET, MRI, topogram, metadata for one subject |
18+
| `/data/output/` | read-write | write your prediction here |
19+
20+
Your container must write the predicted CT to **`/data/output/ct.nii.gz`** — a NIfTI file in Hounsfield units with the same shape and affine as `features/nacpet.nii.gz`.
21+
22+
---
23+
24+
## Requirements
25+
26+
- All model weights baked into the image — network is disabled at runtime (`--network none`)
27+
- Output within 5 minutes (hardware: 1× NVIDIA A40, 2× Xeon Gold 6346, 128 GB RAM)
28+
- No other mounts — do not rely on paths outside `/data/`
29+
30+
---
31+
32+
## Baseline as a Starting Point
33+
34+
The baseline Dockerfile lives at `src/baseline/v2/inference/docker/Dockerfile`. It uses a PyTorch base image, installs dependencies from `requirements.txt`, copies code and weights, and sets the inference script as the entrypoint. Use it as a template.
35+
36+
The key adaptation for any submission is reading inputs from `/data/features/` and writing output to `/data/output/`:
37+
38+
```python
39+
FEATURES_DIR = Path("/data/features")
40+
OUTPUT_DIR = Path("/data/output")
41+
42+
# ...run your model...
43+
44+
# Copy affine from NAC-PET to guarantee shape/affine match
45+
ref = nib.load(str(FEATURES_DIR / "nacpet.nii.gz"))
46+
OUTPUT_DIR.mkdir(parents=True, exist_ok=True)
47+
nib.save(nib.Nifti1Image(pred_hu, ref.affine, ref.header), str(OUTPUT_DIR / "ct.nii.gz"))
48+
```
49+
50+
---
51+
52+
## Submitting
53+
54+
Save your image and email it (or a download link) to **bic-mac-challenge@github.io**:
55+
56+
```bash
57+
docker save my-model:latest | gzip > my-model.tar.gz
58+
```
59+
60+
Subject line: `[DRY-RUN] <TeamName>` or `[FINAL] <TeamName>`
61+
62+
See [submission-guide.md](submission-guide.md) for phase details.
63+
64+
---
65+
66+
## Common Pitfalls
67+
68+
**Hardcoded paths** — make sure your container reads from `/data/features/`, not from training-time paths.
69+
70+
**Affine mismatch** — always copy the header from `features/nacpet.nii.gz` when saving output; don't derive it from an intermediate resampled volume.
71+
72+
**Network downloads at runtime**`torch.hub`, `huggingface_hub`, etc. will fail. Bake weights in during `docker build`.

docs/pet-background.md

Lines changed: 120 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,120 @@
1+
# PET Imaging Background
2+
3+
This guide is for participants who are familiar with medical imaging (MRI, CT) but have not worked extensively with PET. It covers the concepts you need to understand the challenge task, the data, and the evaluation metrics.
4+
5+
---
6+
7+
## What is PET?
8+
9+
**Positron Emission Tomography (PET)** is a functional imaging modality. Unlike CT or MRI, which image anatomy, PET images *metabolic activity*: how actively tissues are taking up a radiotracer.
10+
11+
The most common radiotracer is **FDG** (fluorodeoxyglucose), a glucose analogue. Tissues with high metabolic activity (tumors, brain, heart) accumulate more FDG. The radiotracer emits positrons, which annihilate with electrons to produce two 511 keV gamma rays traveling in opposite directions. Coincident detection of these pairs is what forms the signal.
12+
13+
The raw detector data — called a **sinogram** — captures projection counts at different angles and offsets, analogous to a CT sinogram. From this, an image is reconstructed (usually with iterative algorithms like **OSEM**).
14+
15+
---
16+
17+
## The Attenuation Problem
18+
19+
511 keV photons passing through tissue are attenuated (absorbed or scattered). Without correcting for this, tissues deep inside the body appear artificially dim — the reconstructed image would be quantitatively wrong.
20+
21+
**Attenuation correction (AC)** compensates for this by estimating how much signal was lost along each line of response. The correction factor for each line depends on the total attenuation integral through the body along that path.
22+
23+
In clinical **PET/CT** scanners, a CT scan acquired immediately before the PET scan provides the attenuation map:
24+
25+
1. Convert CT Hounsfield units → **linear attenuation coefficients at 511 keV** (the μ-map)
26+
2. Forward-project the μ-map to compute the **Attenuation Correction Factor (ACF)** sinogram
27+
3. Apply the ACF to the raw PET sinogram before reconstruction
28+
29+
CT is the primary source of radiation dose in a PET/CT exam. Eliminating it by predicting a pseudo-CT from non-ionizing inputs (NAC-PET, MRI) is particularly important for radiation-sensitive populations: children, pregnant patients, and patients requiring frequent follow-up scans.
30+
31+
---
32+
33+
## HU → μ Conversion
34+
35+
Hounsfield units (HU) encode X-ray attenuation relative to water (water = 0 HU, air = −1000 HU). The conversion to linear attenuation coefficients at 511 keV follows a **bilinear model** (Carney et al. 2006):
36+
37+
| Tissue | HU range | Formula |
38+
|--------|----------|---------|
39+
| Air / soft tissue | HU ≤ 0 | μ = 9.6 × 10⁻⁵ × (HU + 1000) |
40+
| Bone | HU > 0 | μ = 9.6 × 10⁻⁵ × 1000 + bone_slope × HU |
41+
42+
The bone slope depends on X-ray tube voltage (kVp). This challenge uses 120 kVp (bone_slope = 5.10 × 10⁻⁵ cm⁻¹/HU).
43+
44+
The resulting μ-map has units of cm⁻¹ and is used directly in the reconstruction pipeline.
45+
46+
---
47+
48+
## What is a Sinogram?
49+
50+
A sinogram stores the raw measured (or corrected) projection data from the PET detector ring. Each row corresponds to a different angular view; each column to a different radial offset. Together they encode the line-integral of activity along every line of response sampled by the detector.
51+
52+
The challenge dataset provides three sinograms per subject (under `recon/`):
53+
54+
| File | Contents |
55+
|------|---------|
56+
| `prompts_rd85.*` | Raw prompt coincidences (signal + background) |
57+
| `mult_nac_rd85.*` | Multiplicative corrections (normalization, detector efficiency, decay) |
58+
| `add_nac_rd85.*` | Additive background estimate (scatter + randoms) |
59+
60+
You do **not** need to work with sinograms directly — the reconstruction pipeline (`src/recon/`) handles everything. But understanding that your pseudo-CT affects the ACF, which is applied to these sinograms before reconstruction, explains why CT accuracy matters for PET quality.
61+
62+
---
63+
64+
## Standardized Uptake Value (SUV)
65+
66+
Raw PET voxel values are proportional to activity concentration (MBq/mL) but vary with injected dose and patient weight — making cross-patient comparisons difficult. **SUV** normalizes for this:
67+
68+
$$\text{SUV} = \frac{\text{voxel activity concentration [kBq/mL]}}{\text{injected dose [kBq] / body weight [g]}}$$
69+
70+
In this challenge, injected dose metadata is not available. Instead, SUV is estimated using the total PET signal and the body mask volume as a weight proxy — consistent across all comparisons.
71+
72+
A perfect pseudo-CT that introduces no attenuation error would produce the same SUV distribution as the ground-truth CT-AC PET. Errors in the μ-map cause regional SUV biases, which the evaluation metrics quantify.
73+
74+
---
75+
76+
## Why MRI + Topogram?
77+
78+
Predicting a CT-quality attenuation map from PET alone is difficult — the NAC-PET has poor tissue contrast and geometric distortion from attenuation effects. MRI and the topogram add complementary anatomical information:
79+
80+
- **DIXON MRI**: A fat/water separation sequence. The in-phase and out-of-phase images allow segmentation of fat vs. soft tissue, which is critical for accurate μ values in adipose-rich regions. Four bed positions (chunks) cover the whole body.
81+
- **Topogram (scout)**: A 2D projection radiograph (like a low-dose planar X-ray) acquired before the main CT. It shows the patient silhouette and bone structure from one projection angle.
82+
83+
Participants are expected to incorporate all available modalities. The baseline model uses NAC-PET only and serves as a lower bound.
84+
85+
---
86+
87+
## The Scanner Setup
88+
89+
Subjects in this challenge were scanned on:
90+
91+
- **Siemens Biograph Vision Quadra** (PET/CT): A long axial field of view (LAFOV) PET scanner with a 106 cm detector ring — it can image the full body in a single bed position but uses multiple bed positions for optimal sensitivity. Ring spacing: 3.29114 mm.
92+
- **Siemens MAGNETOM Vida** (3T MRI): Standard clinical 3T scanner. The DIXON sequence acquires four echoes per TR, enabling fat/water separation from the phase difference of in-phase and out-of-phase images.
93+
94+
Both scanners produce images in the same physical coordinate frame after registration. All data in the dataset has been resampled to the CT grid for consistency.
95+
96+
---
97+
98+
## Summary: What You Are Predicting
99+
100+
Your model receives (per subject):
101+
102+
- `features/nacpet.nii.gz` — NAC-PET volume (low tissue contrast, correlated with uptake)
103+
- `features/mri_chunk_*_*.nii.gz` — DIXON MRI bed positions (good soft tissue contrast)
104+
- `features/mri_combined_*.nii.gz` — Stitched whole-body DIXON
105+
- `features/topogram.nii.gz` — 2D scout image
106+
- `features/metadata.json` — sex, age, height, weight
107+
108+
And must output:
109+
110+
- `ct.nii.gz` — pseudo-CT in Hounsfield units, same shape and affine as the input NAC-PET
111+
112+
This pseudo-CT is then fed into the reconstruction pipeline, which produces an AC-corrected PET image. Both the CT and PET outputs are evaluated against ground truth.
113+
114+
---
115+
116+
## Further Reading
117+
118+
- Carney et al. (2006) — *"Method for Transforming CT Images for Attenuation Correction in PET/CT Scanners"*, Medical Physics. The bilinear HU→μ model used in this challenge.
119+
- Townsend (2008) — *"Multimodality Imaging of Structure and Function"*, Physics in Medicine and Biology. Good clinical PET/CT overview.
120+
- Thielemans et al. (2012) — *"STIR: Software for Tomographic Image Reconstruction Release 2"*, Physics in Medicine and Biology. The reconstruction library used in this challenge.

0 commit comments

Comments
 (0)