Skip to content

About

Hand Bone Segmentation Competition

Resources

Stars

0 stars

Watchers

0 watching

Forks

ย 
ย 

Repository files navigation

๐Ÿฆด X-Ray Bone Segmentation

์† X-Ray ์ด๋ฏธ์ง€์—์„œ ๋ผˆ๋ฅผ 29๊ฐœ ํด๋ž˜์Šค๋กœ ์„ธ๊ทธ๋ฉ˜ํ…Œ์ด์…˜ํ•˜๋Š” ๋”ฅ๋Ÿฌ๋‹ ํ”„๋กœ์ ํŠธ์ž…๋‹ˆ๋‹ค. ์ž์„ธํ•œ ํ”„๋กœ์ ํŠธ ์ง„ํ–‰ ๋‚ด์šฉ์€ WrapUpReport๋ฅผ ์ฐธ๊ณ ํ•ด์ฃผ์„ธ์š”!

WrapUpReport

๐Ÿ“‹ ๋ชฉ์ฐจ

  1. ํ”„๋กœ์ ํŠธ ๊ตฌ์กฐ
  2. ํ™˜๊ฒฝ ์„ค์ •
  3. ๋น ๋ฅธ ์‹œ์ž‘
  4. ์‹คํ—˜ ์ง„ํ–‰ ๋ฐฉ๋ฒ•
  5. ์„ค์ • ํŒŒ์ผ ๊ฐ€์ด๋“œ
  6. WandB ์‚ฌ์šฉ๋ฒ•
  7. TTA (Test Time Augmentation)
  8. ์•™์ƒ๋ธ” (Ensemble)
  9. ํ˜‘์—… ๊ทœ์น™
  10. ๋Œ€ํšŒ ์ œ์ถœ์šฉ CSV ์ƒ์„ฑ
  11. ํŠธ๋Ÿฌ๋ธ”์ŠˆํŒ…
  12. ์‹คํ—˜ ์ฒดํฌ๋ฆฌ์ŠคํŠธ
  13. 29๊ฐœ ํด๋ž˜์Šค ๋ชฉ๋ก

๐Ÿ“ ํ”„๋กœ์ ํŠธ ๊ตฌ์กฐ

Xray-Segmentation/
โ”œโ”€โ”€ .gitignore          # Git ๋ฌด์‹œ ํŒŒ์ผ ๋ชฉ๋ก
โ”œโ”€โ”€ README.md           # ์ด ํŒŒ์ผ
โ”œโ”€โ”€ requirements.txt    # ํ•„์š” ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ๋ชฉ๋ก
โ”œโ”€โ”€ main.py             # ํ•™์Šต/์ถ”๋ก  ๋ฉ”์ธ ์ฝ”๋“œ
โ”œโ”€โ”€ configs/            # ์‹คํ—˜ ์„ค์ • ํŒŒ์ผ (YAML)
โ”‚   โ”œโ”€โ”€ base_config.yaml         # ๊ธฐ๋ณธ ์„ค์ • ํ…œํ”Œ๋ฆฟ
โ”‚   โ”œโ”€โ”€ exp01_fcn_resnet50.yaml  # ์‹คํ—˜ 1: FCN ๋ฒ ์ด์Šค๋ผ์ธ
โ”‚   โ”œโ”€โ”€ exp02_loss_experiment.yaml    # ์‹คํ—˜ 2: Loss ์‹คํ—˜
โ”‚   โ””โ”€โ”€ exp03_augmentation.yaml  # ์‹คํ—˜ 3: Augmentation ์‹คํ—˜
โ”œโ”€โ”€ src/                # ํ•ต์‹ฌ ์ฝ”๋“œ ๋ชจ๋“ˆ
โ”‚   โ”œโ”€โ”€ __init__.py
โ”‚   โ”œโ”€โ”€ dataset.py      # ๋ฐ์ดํ„ฐ์…‹ ํด๋ž˜์Šค
โ”‚   โ”œโ”€โ”€ models.py       # ๋ชจ๋ธ ์ •์˜
โ”‚   โ”œโ”€โ”€ losses.py       # Loss ํ•จ์ˆ˜
โ”‚   โ””โ”€โ”€ utils.py        # ์œ ํ‹ธ๋ฆฌํ‹ฐ ํ•จ์ˆ˜
โ”œโ”€โ”€ notebooks/          # (์ƒ์„ฑ ํ•„์š”) EDA, ๊ฐœ์ธ ์‹คํ—˜์šฉ ๋…ธํŠธ๋ถ
โ”œโ”€โ”€ data/               # (Git ๋ฌด์‹œ) ๋ฐ์ดํ„ฐ์…‹ ์‹ฌ๋ณผ๋ฆญ ๋งํฌ ๋˜๋Š” ๋ณต์‚ฌ
โ””โ”€โ”€ saved_models/       # (Git ๋ฌด์‹œ) ํ•™์Šต๋œ ๋ชจ๋ธ ์ €์žฅ

โš™๏ธ ํ™˜๊ฒฝ ์„ค์ •

1. ์ €์žฅ์†Œ ํด๋ก 

git clone [repository-url]
cd Xray-Segmentation

2. ๊ฐ€์ƒํ™˜๊ฒฝ ์ƒ์„ฑ (๊ถŒ์žฅ)

# conda ์‚ฌ์šฉ์‹œ
conda create -n xray python=3.10
conda activate xray

# ๋˜๋Š” venv ์‚ฌ์šฉ์‹œ
python -m venv venv
source venv/bin/activate  # Linux/Mac
# venv\Scripts\activate   # Windows

3. ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ์„ค์น˜

pip install -r requirements.txt

# PyTorch GPU ๋ฒ„์ „ ์„ค์น˜ (CUDA 11.8 ๊ธฐ์ค€)
pip install torch torchvision --index-url https://download.pytorch.org/whl/cu118

4. ๋ฐ์ดํ„ฐ ๊ฒฝ๋กœ ์„ค์ •

๋ฐ์ดํ„ฐ๋Š” Git์— ์˜ฌ๋ฆฌ์ง€ ์•Š์œผ๋ฏ€๋กœ ์‹ฌ๋ณผ๋ฆญ ๋งํฌ ๋˜๋Š” config ํŒŒ์ผ ์ˆ˜์ •์œผ๋กœ ์—ฐ๊ฒฐํ•ฉ๋‹ˆ๋‹ค.

# ๋ฐฉ๋ฒ• 1: ์‹ฌ๋ณผ๋ฆญ ๋งํฌ ์ƒ์„ฑ
ln -s /path/to/Xray-Segmentation/data/train
ln -s /path/to/Xray-Segmentation/data/test

# ๋ฐฉ๋ฒ• 2: config ํŒŒ์ผ์—์„œ ์ง์ ‘ ๊ฒฝ๋กœ ์ˆ˜์ •
# configs/base_config.yaml์˜ data ์„น์…˜ ์ˆ˜์ •

๐Ÿš€ ๋น ๋ฅธ ์‹œ์ž‘

ํ•™์Šต ์‹คํ–‰

# ๊ธฐ๋ณธ ์‹คํ—˜ (FCN ResNet50)
python main.py --config configs/exp01_fcn_resnet50.yaml --mode train

# Loss ์‹คํ—˜ (BCE + Dice)
python main.py --config configs/exp02_loss_experiment.yaml --mode train

# Augmentation ์‹คํ—˜
python main.py --config configs/exp03_augmentation.yaml --mode train

์ถ”๋ก  ์‹คํ–‰

# ๋ฐฉ๋ฒ• 1: main.py ์‚ฌ์šฉ (config ํŒŒ์ผ ํ•„์š”)
python main.py --config configs/exp01_fcn_resnet50.yaml --mode inference

# ๋ฐฉ๋ฒ• 2: inference.py ์‚ฌ์šฉ (๋” ๊ฐ„๋‹จ!)
python inference.py --config configs/exp01_fcn_resnet50.yaml

# ๋ฐฉ๋ฒ• 3: ๋ชจ๋ธ ๊ฒฝ๋กœ ์ง์ ‘ ์ง€์ •
python inference.py --model saved_models/exp01/best_model.pt --output output.csv

# ๋ฐฉ๋ฒ• 4: ์ƒ์„ธ ์˜ต์…˜ ์ง€์ •
python inference.py --model saved_models/exp01/best_model.pt \
                    --model_name fcn_resnet50 \
                    --test_root data/test/DCM \
                    --output my_submission.csv \
                    --threshold 0.5

# ๋ฐฉ๋ฒ• 5: TTA ์‚ฌ์šฉ (์„ฑ๋Šฅ ํ–ฅ์ƒ!)
python inference.py --config configs/exp01_fcn_resnet50.yaml --tta
python inference.py --model saved_models/exp01/best_model.pt --tta --output output_tta.csv

ํ•™์Šต + ์ถ”๋ก  ํ•œ๋ฒˆ์—

python main.py --config configs/exp01_fcn_resnet50.yaml --mode all

๐Ÿงช ์‹คํ—˜ ์ง„ํ–‰ ๋ฐฉ๋ฒ•

Step 1: ์ƒˆ ์‹คํ—˜ ์„ค์ • ํŒŒ์ผ ์ƒ์„ฑ

# base_config.yaml์„ ๋ณต์‚ฌํ•˜์—ฌ ์ƒˆ ์‹คํ—˜ ํŒŒ์ผ ์ƒ์„ฑ
cp configs/base_config.yaml configs/exp04_your_experiment.yaml

Step 2: ์„ค์ • ํŒŒ์ผ ์ˆ˜์ •

# configs/exp04_your_experiment.yaml

experiment:
  name: "exp04_deeplabv3"           # โœ๏ธ ์‹คํ—˜ ์ด๋ฆ„ ์ˆ˜์ •
  description: "DeepLabV3 ์‹คํ—˜"      # โœ๏ธ ์„ค๋ช… ์ถ”๊ฐ€
  author: "your_name"               # โœ๏ธ ๋ณธ์ธ ์ด๋ฆ„

model:
  name: "deeplabv3_resnet101"       # โœ๏ธ ๋ชจ๋ธ ๋ณ€๊ฒฝ
  pretrained: true

loss:
  name: "bce_dice"                  # โœ๏ธ Loss ๋ณ€๊ฒฝ
  bce_weight: 0.5
  dice_weight: 0.5

save:
  dir: "saved_models/exp04_deeplabv3"  # โœ๏ธ ์ €์žฅ ํด๋” ์ˆ˜์ •

Step 3: ํ•™์Šต ์‹คํ–‰

python main.py --config configs/exp04_your_experiment.yaml --mode train

Step 4: ๊ฒฐ๊ณผ ๊ธฐ๋ก

์‹คํ—˜ ๊ฒฐ๊ณผ๋ฅผ ํŒ€ ๋…ธ์…˜์ด๋‚˜ ์Šคํ”„๋ ˆ๋“œ์‹œํŠธ์— ๊ธฐ๋กํ•ฉ๋‹ˆ๋‹ค.


๐Ÿ“ ์„ค์ • ํŒŒ์ผ ๊ฐ€์ด๋“œ

๐Ÿ—๏ธ ์‚ฌ์šฉ ๊ฐ€๋Šฅํ•œ ๋ชจ๋ธ

๋ชจ๋ธ๋ช… ์„ค๋ช… ๋ฉ”๋ชจ๋ฆฌ ์‚ฌ์šฉ๋Ÿ‰
fcn_resnet50 FCN with ResNet50 ๋‚ฎ์Œ
fcn_resnet101 FCN with ResNet101 ์ค‘๊ฐ„
deeplabv3_resnet50 DeepLabV3 with ResNet50 ์ค‘๊ฐ„
deeplabv3_resnet101 DeepLabV3 with ResNet101 ๋†’์Œ
deeplabv3_mobilenet DeepLabV3 with MobileNet ๋‚ฎ์Œ
model:
  name: "deeplabv3_resnet101"  # ์›ํ•˜๋Š” ๋ชจ๋ธ ์„ ํƒ
  pretrained: true

๐Ÿ“‰ ์‚ฌ์šฉ ๊ฐ€๋Šฅํ•œ Loss ํ•จ์ˆ˜

Loss๋ช… ์„ค๋ช… ์‚ฌ์šฉ ์ƒํ™ฉ
bce Binary Cross Entropy ๊ธฐ๋ณธ ๋ฒ ์ด์Šค๋ผ์ธ
dice Dice Loss ํด๋ž˜์Šค ๋ถˆ๊ท ํ˜•
bce_dice BCE + Dice ์กฐํ•ฉ ์•ˆ์ •์ ์ธ ํ•™์Šต
focal Focal Loss ์‹ฌํ•œ ํด๋ž˜์Šค ๋ถˆ๊ท ํ˜•
tversky Tversky Loss FP/FN ๊ฐ€์ค‘์น˜ ์กฐ์ ˆ
# BCE๋งŒ ์‚ฌ์šฉ
loss:
  name: "bce"

# BCE + Dice ์กฐํ•ฉ
loss:
  name: "bce_dice"
  bce_weight: 0.5    # BCE ๊ฐ€์ค‘์น˜
  dice_weight: 0.5   # Dice ๊ฐ€์ค‘์น˜

# Focal Loss
loss:
  name: "focal"
  alpha: 0.25        # ์–‘์„ฑ ํด๋ž˜์Šค ๊ฐ€์ค‘์น˜
  gamma: 2.0         # focusing parameter

# Tversky Loss
loss:
  name: "tversky"
  alpha: 0.3         # FP ๊ฐ€์ค‘์น˜
  beta: 0.7          # FN ๊ฐ€์ค‘์น˜

๐Ÿ”„ Augmentation ์˜ต์…˜

augmentation:
  train:
    resize: 512                # ์ด๋ฏธ์ง€ ํฌ๊ธฐ
    horizontal_flip: false     # ์ขŒ์šฐ ๋ฐ˜์ „ (X-ray๋Š” ์ฃผ์˜)
    vertical_flip: false       # ์ƒํ•˜ ๋ฐ˜์ „
    rotate: true               # ํšŒ์ „
    rotate_limit: 15           # ํšŒ์ „ ๊ฐ๋„ ๋ฒ”์œ„ (ยฑ15๋„)
    brightness_contrast: true  # ๋ฐ๊ธฐ/๋Œ€๋น„ ์กฐ์ ˆ
    elastic_transform: true    # Elastic ๋ณ€ํ˜•
    grid_distortion: true      # Grid ์™œ๊ณก
  valid:
    resize: 512

๐ŸŽ“ ํ•™์Šต ํŒŒ๋ผ๋ฏธํ„ฐ

training:
  epochs: 50              # ์ด ์—ํญ ์ˆ˜
  batch_size: 8           # ๋ฐฐ์น˜ ํฌ๊ธฐ (GPU ๋ฉ”๋ชจ๋ฆฌ์— ๋”ฐ๋ผ ์กฐ์ ˆ)
  learning_rate: 0.0001   # ํ•™์Šต๋ฅ 
  weight_decay: 0.000001  # ๊ฐ€์ค‘์น˜ ๊ฐ์‡ 
  optimizer: "adam"       # adam, adamw, sgd
  scheduler: "cosine"     # null, cosine, step
  val_every: 5            # ๊ฒ€์ฆ ์ฃผ๊ธฐ
  num_workers: 4          # DataLoader ์›Œ์ปค ์ˆ˜
  n_splits: 5             # K-Fold ์ˆ˜
  fold: 0                 # ์‚ฌ์šฉํ•  fold (0~4)

๐Ÿ“Š WandB ์‚ฌ์šฉ๋ฒ•

1. WandB ์ดˆ๊ธฐ ์„ค์ •

# wandb ๋กœ๊ทธ์ธ (์ฒ˜์Œ ํ•œ ๋ฒˆ๋งŒ)
wandb login

# API ํ‚ค ์ž…๋ ฅ (https://wandb.ai/authorize ์—์„œ ํ™•์ธ)

2. Config ํŒŒ์ผ ์„ค์ •

# ๐Ÿ“Š WandB ์„ค์ •
wandb:
  enabled: true                       # false๋กœ ๋„๋ฉด ๋กœ๊น… ์•ˆํ•จ
  entity: "let_cv_03"                 # ํŒ€ entity ์ด๋ฆ„ (๋ณ€๊ฒฝ ๊ธˆ์ง€!)
  project: "segmentation"             # ํ”„๋กœ์ ํŠธ ์ด๋ฆ„ (๋ณ€๊ฒฝ ๊ธˆ์ง€!)
  name: "gh_fcn_resnet50_epoch50"     # โš ๏ธ ์‹คํ—˜ ์ด๋ฆ„ (ํ•„์ˆ˜ ์ˆ˜์ •!)
  tags: ["baseline", "fcn"]           # ํƒœ๊ทธ (์„ ํƒ)
  notes: "FCN ๋ฒ ์ด์Šค๋ผ์ธ ์‹คํ—˜"          # ๋ฉ”๋ชจ (์„ ํƒ)

3. ์‹คํ—˜ ์ด๋ฆ„ ๋„ค์ด๋ฐ ๊ทœ์น™

ํ˜•์‹: ์ด๋‹ˆ์…œ_๋ชจ๋ธ_์ถ”๊ฐ€์ •๋ณด

์˜ˆ์‹œ ์„ค๋ช…
gh_fcn_resnet50_baseline ๊ฐ€ํ˜„, FCN ResNet50 ๋ฒ ์ด์Šค๋ผ์ธ
jh_deeplabv3_bce_dice ์ง€ํ›ˆ, DeepLabV3 BCE+Dice Loss
sm_unet_augmentation ์ˆ˜๋ฏผ, UNet Augmentation ์‹คํ—˜
yj_fcn_cosine_lr ์˜์ค€, FCN Cosine LR ์Šค์ผ€์ค„๋Ÿฌ

4. WandB ๋Œ€์‹œ๋ณด๋“œ ํ™•์ธ

์‹คํ—˜ ์‹คํ–‰ ํ›„ ์•„๋ž˜ ์ฃผ์†Œ์—์„œ ๊ฒฐ๊ณผ ํ™•์ธ:

5. ๋กœ๊น…๋˜๋Š” ํ•ญ๋ชฉ

ํ•ญ๋ชฉ ์„ค๋ช…
train/step_loss ๋งค step loss
train/epoch_loss ์—ํญ ํ‰๊ท  loss
train/learning_rate ํ˜„์žฌ learning rate
val/loss ๊ฒ€์ฆ loss
val/dice ๊ฒ€์ฆ ํ‰๊ท  Dice
val_dice/{class} ํด๋ž˜์Šค๋ณ„ Dice
val/predictions ๐Ÿ–ผ๏ธ ์‹œ๊ฐํ™” ์ด๋ฏธ์ง€ (Input, GT, Prediction)
best_dice ์ตœ๊ณ  Dice (summary)
best_epoch ์ตœ๊ณ  ์„ฑ๋Šฅ ์—ํญ (summary)

5-1. ๐Ÿ–ผ๏ธ Validation ์‹œ๊ฐํ™”

validation๋งˆ๋‹ค ์ž๋™์œผ๋กœ ์˜ˆ์ธก ๊ฒฐ๊ณผ๊ฐ€ WandB์— ์ด๋ฏธ์ง€๋กœ ๋กœ๊น…๋ฉ๋‹ˆ๋‹ค!

์‹œ๊ฐํ™”๋˜๋Š” ๋‚ด์šฉ:

  • Input: ์›๋ณธ X-Ray ์ด๋ฏธ์ง€
  • Ground Truth: ์‹ค์ œ ์ •๋‹ต ๋งˆ์Šคํฌ (์ƒ‰์ƒ๋ณ„ ํด๋ž˜์Šค)
  • Prediction: ๋ชจ๋ธ ์˜ˆ์ธก ๋งˆ์Šคํฌ

ํ™•์ธ ๋ฐฉ๋ฒ•:

  1. WandB ๋Œ€์‹œ๋ณด๋“œ ์ ‘์†
  2. ํ•ด๋‹น run ํด๋ฆญ
  3. Media ํƒญ ๋˜๋Š” Charts โ†’ val/predictions ํ™•์ธ

์‹œ๊ฐํ™” ์ƒ˜ํ”Œ ์ˆ˜ ์กฐ์ ˆ:

wandb:
  num_vis_samples: 4    # 0์œผ๋กœ ์„ค์ •ํ•˜๋ฉด ์‹œ๊ฐํ™” ์•ˆํ•จ

6. WandB ๋„๊ธฐ

๋กœ์ปฌ ํ…Œ์ŠคํŠธ์‹œ wandb๋ฅผ ๋„๋ ค๋ฉด:

wandb:
  enabled: false    # false๋กœ ๋ณ€๊ฒฝ

7. ์ž์ฃผ ์‚ฌ์šฉํ•˜๋Š” WandB ๊ธฐ๋Šฅ

# ์˜คํ”„๋ผ์ธ ๋ชจ๋“œ๋กœ ์‹คํ–‰ (์ธํ„ฐ๋„ท ์—†์„ ๋•Œ)
WANDB_MODE=offline python main.py --config configs/exp01.yaml --mode train

# ์‹คํ–‰ ํ›„ ๋‚˜์ค‘์— sync
wandb sync ./wandb/offline-run-*

๐Ÿ”„ TTA (Test Time Augmentation)

TTA๋Š” ํ…Œ์ŠคํŠธ/์ถ”๋ก  ์‹œ ์—ฌ๋Ÿฌ augmentation์„ ์ ์šฉํ•˜์—ฌ ์˜ˆ์ธก์„ ์•™์ƒ๋ธ”ํ•˜๋Š” ๊ธฐ๋ฒ•์ž…๋‹ˆ๋‹ค. ์ผ๋ฐ˜์ ์œผ๋กœ 0.5~2% Dice score ํ–ฅ์ƒ์„ ๊ธฐ๋Œ€ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

1. TTA ๊ธฐ๋ณธ ์‚ฌ์šฉ๋ฒ•

# CLI์—์„œ --tta ํ”Œ๋ž˜๊ทธ ์‚ฌ์šฉ
python inference.py --config configs/exp01.yaml --tta

# ๋ชจ๋ธ ์ง์ ‘ ์ง€์ • + TTA
python inference.py --model saved_models/best_model.pt --tta --output output_tta.csv

2. Config ํŒŒ์ผ์—์„œ TTA ์„ค์ •

inference:
  threshold: 0.5
  batch_size: 2                    # TTA ์‚ฌ์šฉ ์‹œ ๋ฉ”๋ชจ๋ฆฌ ๊ณ ๋ คํ•˜์—ฌ ์ž‘๊ฒŒ
  output_csv: "output_tta.csv"
  
  # ๐Ÿ”„ TTA ์„ค์ •
  tta:
    enabled: true                  # TTA ํ™œ์„ฑํ™”
    horizontal_flip: true          # ์ˆ˜ํ‰ ๋’ค์ง‘๊ธฐ (๊ถŒ์žฅ)
    vertical_flip: false           # ์ˆ˜์ง ๋’ค์ง‘๊ธฐ
    rotate90: false                # 90๋„ ๋‹จ์œ„ ํšŒ์ „
    merge_mode: "mean"             # "mean" ๋˜๋Š” "max"

3. TTA ๋ณ€ํ™˜ ์˜ต์…˜ ์„ค๋ช…

์˜ต์…˜ ์„ค๋ช… ํšจ๊ณผ ์‹œ๊ฐ„ ์ฆ๊ฐ€
horizontal_flip ์ขŒ์šฐ ๋ฐ˜์ „ โญโญโญ ๊ฐ€์žฅ ํšจ๊ณผ์  x2
vertical_flip ์ƒํ•˜ ๋ฐ˜์ „ โญโญ x2
rotate90 90/180/270๋„ ํšŒ์ „ โญ X-ray์—๋Š” ๋น„์ถ”์ฒœ x4

4. TTA ์กฐํ•ฉ๋ณ„ ์ถ”๋ก  ์‹œ๊ฐ„

์กฐํ•ฉ Transform ์ˆ˜ ์ถ”๋ก  ์‹œ๊ฐ„ ๊ถŒ์žฅ๋„
HFlip๋งŒ 2 (์›๋ณธ + HFlip) x2 โญโญโญ ๊ธฐ๋ณธ ๊ถŒ์žฅ
HFlip + VFlip 4 (์›๋ณธ + HFlip + VFlip + HVFlip) x4 โญโญ
๋ชจ๋“  ์˜ต์…˜ 8 x8 โญ ๊ณผ๋„ํ•  ์ˆ˜ ์žˆ์Œ

5. X-ray ์ด๋ฏธ์ง€ ๊ถŒ์žฅ TTA ์„ค์ •

X-ray ์† ์ด๋ฏธ์ง€ ํŠน์„ฑ์„ ๊ณ ๋ คํ•œ ๊ถŒ์žฅ ์„ค์ •:

tta:
  enabled: true
  horizontal_flip: true      # โœ… ์ขŒ/์šฐ ์† ๋Œ€์นญ, ๋งค์šฐ ํšจ๊ณผ์ 
  vertical_flip: false       # โŒ ์†์€ ํŠน์ • ๋ฐฉํ–ฅ์ด๋ผ ํšจ๊ณผ ์ œํ•œ์ 
  rotate90: false            # โŒ X-ray ํŠน์„ฑ์ƒ ๋น„์ถ”์ฒœ
  merge_mode: "mean"         # mean์ด max๋ณด๋‹ค ์•ˆ์ •์ 

6. ์•™์ƒ๋ธ” ๋ฐฉ๋ฒ• (merge_mode)

๋ฐฉ๋ฒ• ์„ค๋ช… ํŠน์ง•
mean ๋ชจ๋“  ์˜ˆ์ธก์˜ ํ‰๊ท  ์•ˆ์ •์ , ๋…ธ์ด์ฆˆ ๊ฐ์†Œ
max ๋ชจ๋“  ์˜ˆ์ธก ์ค‘ ์ตœ๋Œ€๊ฐ’ ๋ฏผ๊ฐ๋„ ๋†’์Œ, FP ์ฆ๊ฐ€ ๊ฐ€๋Šฅ

7. TTA ์‚ฌ์šฉ ์‹œ ์ฃผ์˜์‚ฌํ•ญ

โš ๏ธ ๋ฉ”๋ชจ๋ฆฌ: TTA๋Š” ๋ฉ”๋ชจ๋ฆฌ๋ฅผ ๋” ์‚ฌ์šฉํ•ฉ๋‹ˆ๋‹ค. batch_size๋ฅผ ์ค„์ด์„ธ์š”.

โš ๏ธ ์‹œ๊ฐ„: Transform ์ˆ˜๋งŒํผ ์ถ”๋ก  ์‹œ๊ฐ„์ด ์ฆ๊ฐ€ํ•ฉ๋‹ˆ๋‹ค.

โš ๏ธ ํšจ๊ณผ: ๋ชจ๋“  transform์ด ํ•ญ์ƒ ์ข‹์€ ๊ฑด ์•„๋‹™๋‹ˆ๋‹ค. ๊ฒ€์ฆ ํ›„ ์‚ฌ์šฉํ•˜์„ธ์š”.

# ๋ฉ”๋ชจ๋ฆฌ ๋ถ€์กฑ ์‹œ
inference:
  batch_size: 1              # ๋ฐฐ์น˜ ํฌ๊ธฐ ์ค„์ด๊ธฐ
  tta:
    enabled: true
    horizontal_flip: true    # ํ•„์š”ํ•œ ๊ฒƒ๋งŒ ์‚ฌ์šฉ

๐ŸŽฏ ์•™์ƒ๋ธ” (Ensemble)

์—ฌ๋Ÿฌ ๋ชจ๋ธ์˜ ์˜ˆ์ธก ๊ฒฐ๊ณผ๋ฅผ ๊ฒฐํ•ฉํ•˜์—ฌ ์„ฑ๋Šฅ์„ ํ–ฅ์ƒ์‹œํ‚ค๋Š” ๋ฐฉ๋ฒ•์ž…๋‹ˆ๋‹ค. ์ผ๋ฐ˜์ ์œผ๋กœ 1~3% Dice score ํ–ฅ์ƒ์„ ๊ธฐ๋Œ€ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

1. ๋น ๋ฅธ ์‹œ์ž‘

# CSV ํŒŒ์ผ ์•™์ƒ๋ธ” (๊ฐ€์žฅ ๊ฐ„๋‹จ)
python ensemble.py --csvs output1.csv output2.csv output3.csv \
                   --output ensemble.csv

# ๊ฐ€์ค‘์น˜ ๊ธฐ๋ฐ˜ ์•™์ƒ๋ธ” (์„ฑ๋Šฅ ์ข‹์€ ๋ชจ๋ธ์— ๋†’์€ ๊ฐ€์ค‘์น˜)
python ensemble.py --csvs output1.csv output2.csv output3.csv \
                   --weights 0.5 0.3 0.2 \
                   --method weighted_average \
                   --output ensemble_weighted.csv

# Config ํŒŒ์ผ ์‚ฌ์šฉ (๊ถŒ์žฅ)
python ensemble.py --config configs/ensemble/ensemble_csv_simple.yaml

2. ์ง€์›ํ•˜๋Š” ์•™์ƒ๋ธ” ๋ฐฉ๋ฒ•

๋ฐฉ๋ฒ• ์„ค๋ช…
simple_average ๋ชจ๋“  ๋ชจ๋ธ์˜ ํ™•๋ฅ ๊ฐ’ ํ‰๊ท 
weighted_average ์„ฑ๋Šฅ ๊ธฐ๋ฐ˜ ๊ฐ€์ค‘์น˜ ํ‰๊ท 
max_voting ๊ฐ ํ”ฝ์…€์—์„œ ์ตœ๋Œ€ ํ™•๋ฅ ๊ฐ’ ์„ ํƒ
hard_voting ์ด์ง„ํ™” ํ›„ ๋‹ค์ˆ˜๊ฒฐ
rank_average ์ˆœ์œ„ ๊ธฐ๋ฐ˜ ํ‰๊ท 
geometric_mean ๊ธฐํ•˜ํ‰๊ท 

3. ์‹ค์ „ ์›Œํฌํ”Œ๋กœ์šฐ

# Step 1: ์—ฌ๋Ÿฌ ๋ชจ๋ธ ํ•™์Šต
python main.py --config configs/exp01_unetpp_efficientb4.yaml
python main.py --config configs/exp02_unetpp_mobilenet.yaml
python main.py --config configs/exp03_deeplabv3_resnet50.yaml

# Step 2: ๊ฐ ๋ชจ๋ธ๋กœ ์ถ”๋ก 
python inference.py --config configs/exp01_unetpp_efficientb4.yaml
python inference.py --config configs/exp02_unetpp_mobilenet.yaml
python inference.py --config configs/exp03_deeplabv3_resnet50.yaml

# Step 3: ์•™์ƒ๋ธ”
python ensemble.py --csvs exp01_output.csv exp02_output.csv exp03_output.csv \
                   --method simple_average \
                   --output final_ensemble.csv

4. Config ํŒŒ์ผ ์˜ˆ์‹œ

# configs/ensemble/my_ensemble.yaml

ensemble:
  method: "weighted_average"
  
  csv_files:
    - "exp01_output.csv"  # dice: 0.95
    - "exp02_output.csv"  # dice: 0.93
    - "exp03_output.csv"  # dice: 0.91
  
  # Validation Dice Score ๊ธฐ๋ฐ˜ ๊ฐ€์ค‘์น˜
  weights: [0.5, 0.3, 0.2]
  
  output_csv: "ensemble_output.csv"
  threshold: 0.5

5. ์•™์ƒ๋ธ” ํŒ

โœ… ๋‹ค์–‘์„ฑ ํ™•๋ณด: ์„œ๋กœ ๋‹ค๋ฅธ ์•„ํ‚คํ…์ฒ˜, ๋ฐฑ๋ณธ, ์ด๋ฏธ์ง€ ํฌ๊ธฐ ์‚ฌ์šฉ
โœ… ๊ฐ€์ค‘์น˜ ์„ค์ •: Validation Dice Score ๊ธฐ๋ฐ˜์œผ๋กœ ๊ฐ€์ค‘์น˜ ๋ถ€์—ฌ
โœ… ์ ์ ˆํ•œ ๊ฐœ์ˆ˜: 3~5๊ฐœ ๋ชจ๋ธ์ด ์ผ๋ฐ˜์ ์œผ๋กœ ์ถฉ๋ถ„
โœ… ๋ฐฉ๋ฒ• ์„ ํƒ: Simple Average๋กœ ์‹œ์ž‘, ์„ฑ๋Šฅ ์ฐจ์ด ํฌ๋ฉด Weighted Average

๐Ÿ“š ์ƒ์„ธ ๊ฐ€์ด๋“œ

๋” ์ž์„ธํ•œ ๋‚ด์šฉ์€ ์•™์ƒ๋ธ” ๊ฐ€์ด๋“œ๋ฅผ ์ฐธ๊ณ ํ•˜์„ธ์š”.


๐Ÿค ํ˜‘์—… ๊ทœ์น™

1. Git ๋ธŒ๋žœ์น˜ ์ „๋žต

# ์ƒˆ๋กœ์šด ์‹คํ—˜์€ ๋ณธ์ธ ๋ธŒ๋žœ์น˜์—์„œ ์ง„ํ–‰
git checkout -b exp/ํ™๊ธธ๋™/loss_experiment

# ์ž‘์—… ์™„๋ฃŒ ํ›„ main์— merge
git checkout main
git merge exp/ํ™๊ธธ๋™/loss_experiment

2. ์ปค๋ฐ‹ ๋ฉ”์‹œ์ง€ ๊ทœ์น™

# ํ˜•์‹: [ํƒ€์ž…] ๋‚ด์šฉ

# ์˜ˆ์‹œ
git commit -m "[exp] exp04 Loss ์‹คํ—˜ ์ถ”๊ฐ€"
git commit -m "[fix] dataset ๊ฒฝ๋กœ ๋ฒ„๊ทธ ์ˆ˜์ •"
git commit -m "[feat] Cosine scheduler ์ถ”๊ฐ€"
git commit -m "[docs] README ์‚ฌ์šฉ๋ฒ• ์—…๋ฐ์ดํŠธ"

3. ์‹คํ—˜ ์„ค์ • ํŒŒ์ผ ๋„ค์ด๋ฐ

exp[๋ฒˆํ˜ธ]_[์‹คํ—˜๋‚ด์šฉ].yaml

# ์˜ˆ์‹œ
exp01_fcn_resnet50.yaml      # ๋ชจ๋ธ ์‹คํ—˜
exp02_loss_bce_dice.yaml     # Loss ์‹คํ—˜
exp03_augmentation.yaml       # Augmentation ์‹คํ—˜
exp04_scheduler_cosine.yaml   # ์Šค์ผ€์ค„๋Ÿฌ ์‹คํ—˜

4. ๊ฒฐ๊ณผ ๊ณต์œ 

์‹คํ—˜ ํ›„ ์•„๋ž˜ ์ •๋ณด๋ฅผ ํŒ€๊ณผ ๊ณต์œ ํ•ฉ๋‹ˆ๋‹ค:

ํ•ญ๋ชฉ ๋‚ด์šฉ
์‹คํ—˜ ๋ฒˆํ˜ธ exp04
์‹คํ—˜์ž ํ™๊ธธ๋™
๋ณ€๊ฒฝ ์‚ฌํ•ญ DeepLabV3 + Dice Loss
Best Dice 0.9523
ํ•™์Šต ์‹œ๊ฐ„ 2์‹œ๊ฐ„
ํŠน์ด์‚ฌํ•ญ epoch 30์—์„œ ์ˆ˜๋ ด

๐Ÿ† ๋Œ€ํšŒ ์ œ์ถœ์šฉ CSV ์ƒ์„ฑ

1. ํ•™์Šต ์™„๋ฃŒ ํ›„ CSV ์ƒ์„ฑ

# Config ํŒŒ์ผ ์‚ฌ์šฉ (๊ถŒ์žฅ)
python inference.py --config configs/exp01_fcn_resnet50.yaml

# ๋˜๋Š” ์ง์ ‘ ๋ชจ๋ธ ๊ฒฝ๋กœ ์ง€์ •
python inference.py --model saved_models/exp01/best_model.pt \
                    --output submission.csv

2. inference.py ์˜ต์…˜ ์„ค๋ช…

์˜ต์…˜ ์„ค๋ช… ๊ธฐ๋ณธ๊ฐ’
--config Config yaml ํŒŒ์ผ ๊ฒฝ๋กœ -
--model ํ•™์Šต๋œ ๋ชจ๋ธ ํŒŒ์ผ (.pt) -
--model_name ๋ชจ๋ธ ์ด๋ฆ„ fcn_resnet50
--test_root ํ…Œ์ŠคํŠธ ์ด๋ฏธ์ง€ ๊ฒฝ๋กœ data/test/DCM
--output ์ถœ๋ ฅ CSV ํŒŒ์ผ๋ช… output.csv
--image_size ์ž…๋ ฅ ์ด๋ฏธ์ง€ ํฌ๊ธฐ 512
--threshold ์ด์ง„ํ™” ์ž„๊ณ„๊ฐ’ 0.5
--batch_size ๋ฐฐ์น˜ ํฌ๊ธฐ 2
--tta ๐Ÿ”„ TTA ์‚ฌ์šฉ (์„ฑ๋Šฅ ํ–ฅ์ƒ) false

3. ์ถœ๋ ฅ CSV ํ˜•์‹

image_name,class,rle
image001.png,finger-1,1 5 10 3 ...
image001.png,finger-2,20 8 35 12 ...
...

4. ์ œ์ถœ ์ฒดํฌ๋ฆฌ์ŠคํŠธ

  • ํ…Œ์ŠคํŠธ ๋ฐ์ดํ„ฐ ๊ฒฝ๋กœ๊ฐ€ ์˜ฌ๋ฐ”๋ฅธ๊ฐ€? (data/test/DCM)
  • ํ•™์Šต๋œ ๋ชจ๋ธ ํŒŒ์ผ(.pt)์ด ์กด์žฌํ•˜๋Š”๊ฐ€?
  • ๋ชจ๋ธ ์ด๋ฆ„(--model_name)์ด ํ•™์Šต ๋•Œ์™€ ๋™์ผํ•œ๊ฐ€?
  • CSV ํŒŒ์ผ์ด ์ •์ƒ์ ์œผ๋กœ ์ƒ์„ฑ๋˜์—ˆ๋Š”๊ฐ€?
  • CSV ํŒŒ์ผ ํฌ๊ธฐ๊ฐ€ ์ ์ ˆํ•œ๊ฐ€? (๋นˆ ํŒŒ์ผ ์•„๋‹Œ์ง€)
  • ๐Ÿ”„ TTA ์‚ฌ์šฉ ์—ฌ๋ถ€๋ฅผ ๊ณ ๋ คํ–ˆ๋Š”๊ฐ€? (--tta ํ”Œ๋ž˜๊ทธ)

๐Ÿ”ง ํŠธ๋Ÿฌ๋ธ”์ŠˆํŒ…

CUDA Out of Memory

# ๋ฐฐ์น˜ ์‚ฌ์ด์ฆˆ ์ค„์ด๊ธฐ
training:
  batch_size: 4  # 8 โ†’ 4

# ๋˜๋Š” ์ด๋ฏธ์ง€ ํฌ๊ธฐ ์ค„์ด๊ธฐ
image:
  size: 256  # 512 โ†’ 256

ํ•™์Šต์ด ๋„ˆ๋ฌด ๋А๋ฆผ

# num_workers ๋Š˜๋ฆฌ๊ธฐ
training:
  num_workers: 8  # 4 โ†’ 8

# ๋˜๋Š” ๊ฐ€๋ฒผ์šด ๋ชจ๋ธ ์‚ฌ์šฉ
model:
  name: "deeplabv3_mobilenet"

Dice Score๊ฐ€ ์˜ค๋ฅด์ง€ ์•Š์Œ

# 1. Loss ๋ณ€๊ฒฝ
loss:
  name: "bce_dice"

# 2. Learning rate ์กฐ์ ˆ
training:
  learning_rate: 0.00001  # ์ค„์ด๊ธฐ

# 3. Augmentation ์ถ”๊ฐ€
augmentation:
  train:
    rotate: true
    brightness_contrast: true

๋ฐ์ดํ„ฐ ๊ฒฝ๋กœ ์—๋Ÿฌ

# config ํŒŒ์ผ์˜ ๊ฒฝ๋กœ ํ™•์ธ
data:
  train_image_root: "../Segmentation/train/DCM"
  # ์‹ค์ œ ๊ฒฝ๋กœ๊ฐ€ ๋งž๋Š”์ง€ ํ™•์ธ!

# ์ƒ๋Œ€ ๊ฒฝ๋กœ ๋Œ€์‹  ์ ˆ๋Œ€ ๊ฒฝ๋กœ ์‚ฌ์šฉ
data:
  train_image_root: "/home/user/data/Segmentation/train/DCM"

โœ… ์‹คํ—˜ ์ฒดํฌ๋ฆฌ์ŠคํŠธ

์ƒˆ๋กœ์šด ์‹คํ—˜ ์ „ ํ™•์ธ์‚ฌํ•ญ:

  • ์ƒˆ config ํŒŒ์ผ ์ƒ์„ฑํ–ˆ๋Š”๊ฐ€?
  • ์‹คํ—˜ ์ด๋ฆ„(experiment.name)์„ ๊ณ ์œ ํ•˜๊ฒŒ ์„ค์ •ํ–ˆ๋Š”๊ฐ€?
  • ์ €์žฅ ํด๋”(save.dir)๋ฅผ ์‹คํ—˜๋ณ„๋กœ ๋‹ค๋ฅด๊ฒŒ ์„ค์ •ํ–ˆ๋Š”๊ฐ€?
  • ์ถœ๋ ฅ CSV(inference.output_csv)๋ฅผ ์‹คํ—˜๋ณ„๋กœ ๋‹ค๋ฅด๊ฒŒ ์„ค์ •ํ–ˆ๋Š”๊ฐ€?
  • ์‹คํ—˜์ž ์ด๋ฆ„(experiment.author)์„ ์ž…๋ ฅํ–ˆ๋Š”๊ฐ€?
  • ๋ฐ์ดํ„ฐ ๊ฒฝ๋กœ๊ฐ€ ์˜ฌ๋ฐ”๋ฅธ๊ฐ€?
  • WandB ์„ค์ •: wandb.name์„ ๋ณธ์ธ ์ด๋‹ˆ์…œ + ์‹คํ—˜ ์ •๋ณด๋กœ ์„ค์ •ํ–ˆ๋Š”๊ฐ€?
  • WandB ์„ค์ •: wandb.tags์— ์‹คํ—˜ ํ‚ค์›Œ๋“œ๋ฅผ ์ถ”๊ฐ€ํ–ˆ๋Š”๊ฐ€?

๐Ÿ“Š 29๊ฐœ ํด๋ž˜์Šค ๋ชฉ๋ก

๋ฒˆํ˜ธ ํด๋ž˜์Šค๋ช… ์„ค๋ช…
0-18 finger-1 ~ finger-19 ์†๊ฐ€๋ฝ ๋ผˆ
19 Trapezium ๋Œ€๋Šฅํ˜•๊ณจ
20 Trapezoid ์†Œ๋Šฅํ˜•๊ณจ
21 Capitate ์œ ๋‘๊ณจ
22 Hamate ์œ ๊ตฌ๊ณจ
23 Scaphoid ์ฃผ์ƒ๊ณจ
24 Lunate ์›”์ƒ๊ณจ
25 Triquetrum ์‚ผ๊ฐ๊ณจ
26 Pisiform ๋‘์ƒ๊ณจ
27 Radius ์š”๊ณจ
28 Ulna ์ฒ™๊ณจ

๐Ÿ‘ฅ ํŒ€์›

์ด๋ฆ„ ์—ญํ•  ๋‹ด๋‹น ์‹คํ—˜
๋ฐ•์ƒ๋ฒ” ๋ฉ‹์Ÿ์ด EDA, data preprocessing, loss, augmentation
์•ˆ์ง„๊ฒฝ ๋ฉ‹์Ÿ์ด model, augmentation, feature research
์ด๊ฐ€ํ˜„ ๋ฉ‹์Ÿ์ด setting, model, fine-tuning
์ดํ˜œ์ค€ ๋ฉ‹์Ÿ์ด EDA, data preprocessing, loss, feature research
ํ™ฉ์€๋ฐฐ ๋ฉ‹์Ÿ์ด model, augmentation, feature research

๐Ÿ“š ์ฐธ๊ณ  ์ž๋ฃŒ


Happy Experimenting! ๐Ÿš€

About

Hand Bone Segmentation Competition

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages