Hi!
This 1 month project was developed during the Brainhack School 2026 at Polytechnique Montréal.
Respiratory motion during MRI acquisition introduces artifacts in k-space that degrade image quality. This is particularly critical for spinal cord imaging. This project aim to simulate breathing-induced motion corruption directly in k-space for accelerated MRI and trains a 2D U-Net to correct these artifacts.
Rather than working in image space, the model operates on complex k-space data (real + imaginary channels), which is more faithful to the actual acquisition process and allows correction before reconstruction.
Can deep learning models correct breathing motion-induced artefact on accelerated MRI from corrupted k-space acquisitions ?
The main objectives of my project were:
- Develop a simulation pipeline to generate corrupted k-space with respiratory motion, cartesian undersampling and gaussian noise
- Generate a training dataset by varying the motion (breathing-cycle) amplitude and frequency, the undersampling factor and the noise level
- Train a deep learning model for artifact correction in k-space
- Evaluate the model performance using quantitative image quality metrics
My personal objectives with this project were:
- Learn how deep-learning works
- Learn how to train a model
- Learn how to use high computational ressources
- Learn how to adapt a classical model (2D U-Net) on a specific project
flowchart TD
A[T2w NIfTI volume: ds005616]:::input
B[Clean K-space]:::kspace
C[️Phase Ramp\nMotion : A, f]:::corrupt
D[Cartesian Undersampling\nFactor R]:::corrupt
E[Complex Gaussian Noise\nSNR dB]:::corrupt
F[Corrupted K-space\nreal + imaginary channels]:::kspace
G[2D U-Net\nInput/Output : 2, H, W]:::model
H[Reconstructed Image]:::output
A -->|2D FFT| B
B --> C
B --> D
B --> E
C --> F
D --> F
E --> F
F --> G
G -->|iFFT| H
classDef input fill:#B497E7,stroke:#2C5F8A,color:#fff,rx:8
classDef kspace fill:#F6CF71,stroke:#4B3FA0,color:#fff,rx:8
classDef corrupt fill:#9EB9F3,stroke:#B07820,color:#fff,rx:8
classDef model fill:#F89C74,stroke:#2E8B57,color:#fff,rx:8
classDef output fill:#FF6B6B,stroke:#CC3333,color:#fff,rx:8
To ensure that my project stays open and reproductible I use several tools that are widely use in neuroimaging MRI research:
- OpenNeuro, BIDS format and Datalab: Download only the necessary files of my dataset in a standardized way
- Python and jupyter notebooks: Implement my simulation, processing, and deep learning model training and evaluation pipelines
- Bash: Automate management of my datasets and access advanced computing resources
- Alliance of Canada: Train my deep learning model using high-performance (GPU-accelerated) computing
- GitHub: Document and share my project
The main deliverable of this project is a fully documented GitHub repository containing all necessary files to:
- Reproduce the full project: from simulation to training to inference
- Use the simulation pipeline only: generate motion-corrupted k-space data for your own dataset
- Use the pre-trained model directly: run inference without retraining
- Retrain the model: on a different dataset or with different parameters
See the Repository Structure and Reproducibility Guide sections at the end of this README for a detailed description of the repository contents and how to reproduce any step of this project.
This project uses the Whole-Spine Anatomical MRI dataset (ds005616), available on:
- OpenNeuro: https://openneuro.org/datasets/ds005616/versions/1.1.2
- GitHub: https://github.com/OpenNeuroDatasets/ds005616.git
For this project we use:
- Modality: T2-weighted whole-spine MRI
- Subjects: 56
- Resolution: 1 mm³
- Format: NIfTI (.nii.gz), BIDS-compliant
Data access via Datalad:
datalad install https://github.com/OpenNeuroDatasets/ds005616.git
datalad get sub-*/anat/sub-*_T2w.nii.gzDuring a gradient echo (GRE) MRI acquisition, k-space lines are acquired sequentially over time. Respiratory motion between acquisitions induces a phase shift in each k-space line, modeled as:
where
The animation below illustrates this process: the respiratory signal (top-left), the k-space being filled line by line with the resulting phase ramp (bottom-left), and the reconstructed image showing motion ghosting artifacts (right).
Combined with Cartesian undersampling (acceleration factor R) and complex Gaussian noise, this produces realistic corrupted k-space data for accelerated MRI that impose several typical artifacts on the reconstruted image.
notebooks/Kspace_corruption_simulation_vf.ipynb.
A training dataset was generated my varying the corruption paramters:
| Parameter | Range | Description |
|---|---|---|
| A | 2.0, 5.0, 8.0 px | Motion amplitude |
| f | 12, 15, 18 breaths/min | Respiratory rate |
| R | 2, 4, 6 | Undersampling factor |
| SNR | 15, 20, 25 dB | Signal-to-noise ratio |
Total combinations: 81 per slice → 231,417 training samples across 56 subjects.
Choice of simulation parameters:
- Motion amplitude A: The motion amplitude A (in pixels, assuming 1 mm isotropic resolution) spans the physiological range of respiratory spinal cord displacement measured in vivo. Studies have shown that breathing induces spinal cord displacements are up to 10 mm in the anterior-posterior direction at 3T. At 1 mm/px resolution (ds005616), this translates to A = 1–10 px. I choose to use 2, 5 et 8 px displacement to cover a large range of displacement, 8px being already an important displacement, I choose to not done the 10px being rare et intense above all that the displacement here are applied to the whole image.
Verma, T. and Cohen-Adad, J. (2014). Effect of respiration on the B0 field in the human spinal cord at 3T. Magnetic Resonance in Medicine, 72: 1629–1636. https://doi.org/10.1002/mrm.25075
- Respiratory rate f: The normal respiratory rate for adults at rest ranges from 12 to 20 breaths/min. We use f = 12, 15, 18 breaths/min to cover this physiological range.
Sapra A, Malik A, Bhandari P. Vital Sign Assessment. [Updated 2023 May 1]. In: StatPearls [Internet]. Treasure Island (FL): StatPearls Publishing; 2026 Jan-. Available from: https://www.ncbi.nlm.nih.gov/books/NBK553213/
-
Undersampling factor R: R = 2, 4, 6 corresponds to acquiring around 50%, 25% and 17% of k-space lines respectively, covering the typical acceleration factors used in clinical accelerated MRI protocols.
-
Signal-to-noise ratio SNR: We simulate SNR values of 15, 20 and 25 dB. An SNR above 20 dB is generally considered sufficient for diagnostic image quality.
*McRobbie, D.W., Moore, E.A., Graves, M.J., Prince, M.R. (2017). MRI from Picture to Proton. Cambridge University Press.
2D U-Net with 3 pooling levels:
Input (2, H, W) — real & imaginary corrupted k-space
│
├── Encoder: 32 → 64 → 128 → 256
│ MaxPool2d between levels
│
├── Decoder: 256 → 128 → 64 → 32
│ ConvTranspose2d + skip connections
│
Output (2, H, W) — real & imaginary corrected k-space
Parameters:
- Parameters: ~1.9M
- Optimizer: Adam (lr=1e-3)
- Scheduler: CosineAnnealingLR (T_max=20, eta_min=1e-6)
- Loss: L1 (masked to valid region)
Training was performed on Alliance Canada (Narval) using the SLURM job scheduler:
- GPU: 1× NVIDIA A100 (40 GB)
- CPUs: 8
- RAM: 32 GB
- time=36:00:00
- Epochs: 20
- Batch size: 32
- Framework: PyTorch 2.6
Script arguments:
--data_root: Absolute path to the project root--manifest: Path to the dataset manifest CSV--splits: Path to the train/val/test split JSON--output: Output directory--epochs: Number of training epochs--batch_size: Batch size
The train and loss curves show no overfiiting during training, both curves decrease together throughout the 20 epochs:
The quantitative images quality metrics SSIM et PSNR confirm that the model improves consistently epoch by epoch:
We observe great improvement on the validation set:
- SSIM improved from 0.38 → 0.63
- PSNR improved from 20.9 → 24.1 dB
The following figure shows the predicted k-space alongside the ground truth and the corrupted k-space:
After reconstruction, the corrected image predicted by the model shows a clear reduction of motion ghosting artifacts compared to the corrupted input:
The following figure shows the model's correction across different motion amplitudes (A = 2, 5, 8 px) to assess its robustness to varying artifact severity. The three corrected images all shows a clear reduction of the motion artifacts:
Finally, you can see the correction on axial views. The results are particularly interresting because the spinal cord which had almost disappeared in the corrupted axial slices due to ghosting artifacts is successfully retrieved after model correction:
Note: This project was primarily a learning experience in training and applying deep learning to a specific MRI reconstruction problem. The following limitations reflect the simplified assumptions made in the simulation model.
- 1D rigid translation only along the readout direction -> no rotation, no non-rigid deformation
- Uniform displacement along the spine -> in reality, respiratory motion decreases with distance from the lungs
- No B0 field fluctuations induced by breathing
- Simulated data only -> the model was trained and evaluated exclusively on simulated artifacts
Sarrazin_project/
│
├── src/
│ ├── Kspace_simulation.py # K-space corruption pipeline
│ ├── Utils.py # Metrics and utilities
│ ├── Unet_model.py # 2D U-Net architecture
│ └── Unet_train.py # Training loop
│
├── notebooks/
│ ├── Kspace_corruption_simulan_vf.ipynb # Step-by-step simulation
│ ├── Unet_inference.ipynb # Inference & visualization
│ ├── Unet_analysis.ipynb Training curves & metrics
│ └── Kspace_gif.ipynb # Breathing motion simulation gif
│
├── training_data/
│ ├── manifest.csv # Dataset manifest (path, TR, TE, H, W, params)
│ └── splits.json # Train/val/test subject splits (70/15/15)
│
├── results/
│ ├── unet_best.pt # Best model
│ ├── training_history.csv # Metrics per epoch
│ ├── figures/ # Training evaluation curves
│
├── README_figures/ # Figures and images displayed in this README
├── gif/ # Breathing motion simulation gif displayed in this README
│
├── train_full.sh # SLURM job script (Alliance Canada)
├── requirements.txt # Configuration file
└── README.md
The following set-up use the server Narval on Alliance Canada, you can change it to the server name you want to use
git clone https://github.com/annaellesarrazin/Sarrazin_project.git
cd Sarrazin_projectconda create -n brainhack python=3.10
conda activate brainhack
pip install -r requirements.txtdatalad install https://github.com/OpenNeuroDatasets/ds005616.git
cd ds005616
datalad get sub-*/anat/sub-*_T2w.nii.gz
cd ..rsync -av --progress \
/path/to/Sarrazin_project/ \
username@narval.alliancecan.ca:/scratch/username/Sarrazin_project/# Connect to Narval
ssh username@narval.alliancecan.ca
# Load Python module
module load python/3.10
# Create virtual environment
virtualenv ~/brainhack/brainhack
source ~/brainhack/brainhack/bin/activate
# Install dependencies
pip install torch torchvision
pip install -r requirements.txt# Connect to Narval
ssh username@narval.alliancecan.ca
# Go to the folder Sarrazin_project
cd /scratch/username/Sarrazin_project
# Submit the job — environment activation is handled by train_full.sh
sbatch train_full.sh
# Monitor training
squeue -u $USER # check job status
tail -f logs/unet_*.out # follow live logs# From your local machine
scp username@narval.alliancecan.ca:/scratch/username/Sarrazin_project/results/full_run/{unet_best.pt,training_history.csv} \
results/Open notebooks/Unet_inference.ipynb and set:
MODEL_PATH = Path('results/unet_best.pt')
SPLITS_PATH = Path('training_data/splits.json')Open notebooks/Unet_analysis.ipynb and set:
HISTORY_PATH = Path('results/training_history.csv')Deep learning seems promissing to effectively correct breathing-induced motion artifacts in accelerated MRI k-space.
On a personal level, this project was a great opportunity to learn how works deep learning, and how to train and evaluate a deep learning model for a specific problem. I enjoyed understanding the connections between MRI physics, k-space signal processing, and deep learning. I am looking forward to continue this work in the futur.
- Vannesjo, S. J., Miller, K. L., Clare, S., & Tracey, I. (2018). Spatiotemporal characterization of breathing-induced B0 field fluctuations in the cervical spinal cord at 7T. NeuroImage, 167, 191–202. https://doi.org/10.1016/j.neuroimage.2017.11.031
- Makowski, D., Pham, T., Lau, Z.J., et al. (2021). NeuroKit2: A Python Toolbox for Neurophysiological Signal Processing. Behavior Research Methods. https://doi.org/10.3758/s13428-020-01516-y
- Verma, T. and Cohen-Adad, J. (2014). Effect of respiration on the B0 field in the human spinal cord at 3T. Magnetic Resonance in Medicine, 72: 1629–1636. https://doi.org/10.1002/mrm.25075
- Sapra A, Malik A, Bhandari P. Vital Sign Assessment. StatPearls (internet). Treasure Island (FL): StatPearls Publishing; 2026 Jan-. Available from: https://www.ncbi.nlm.nih.gov/books/NBK553213/
- McRobbie, D.W., Moore, E.A., Graves, M.J., Prince, M.R. (2017). MRI from Picture to Proton. Cambridge University Press (digital acces). Available from: https://www.cambridge.org/core/books/mri-from-picture-to-proton/3ADC814FF8FC6A78A54D37746F806D5A
- Griswold, M.A., Jakob, P.M., Heidemann, R.M., Nittka, M., Jellus, V., Wang, J., Kiefer, B. and Haase, A. (2002), Generalized autocalibrating partially parallel acquisitions (GRAPPA). Magn. Reson. Med., 47: 1202-1210. https://doi.org/10.1002/mrm.10171
Annaelle8
Annaelle Sarrazin — Brainhack School 2026









