📝 Artikel ini ditulis dalam Bahasa Indonesia
🔥 Seri Belajar PyTorch Part 4

Transfer Learning: Pakai Model yang Sudah Pintar

Mengapa train dari nol kalau model sudah belajar dari 14 juta gambar? Part 4 mengajarkan cara menggunakan pre-trained ResNet untuk mengenali objek baru — hanya dengan mengganti "kepala" network. Dari 20% akurasi (train from scratch) ke 96%+ (transfer learning) dalam 5 epoch.

📅 Maret 2026 ⏱ 25 menit baca 🏷 PyTorch • Transfer Learning • ResNet • Fine-Tuning • Pre-trained
📚 Seri Belajar PyTorch:
1 2 3 4 5 6 7 8 9 10

📑 Daftar Isi — Part 4

  1. Mengapa Transfer Learning? — Dari 14 juta gambar ke dataset Anda
  2. ResNet: Skip Connections — Arsitektur yang merevolusi deep learning
  3. 2 Strategi Transfer Learning — Feature extraction vs fine-tuning
  4. Kode: Feature Extraction — Freeze semua, train kepala saja
  5. Kode: Fine-Tuning — Unfreeze sebagian, train bersama
  6. Grad-CAM: Lihat Apa yang Dilihat Model — Visualisasi "attention"
  7. Kapan Pakai Strategi Mana? — Decision framework
  8. Ringkasan & Preview Part 5
🧠

1. Mengapa Transfer Learning?

Train from scratch = buang waktu dan data. Pakai model yang sudah pintar.

Di Part 1-3, kita train model dari nol (random weights). Untuk MNIST (angka sederhana 28×28), ini berhasil. Tapi untuk gambar real-world — kucing vs anjing, bunga, X-ray — kita butuh jutaan gambar dan berhari-hari training. Transfer learning menyelesaikan ini.

🧠 Transfer Learning — Pinjam "Otak" yang Sudah Terlatih

ImageNet Training 14 juta gambar, 1000 kelas Ratusan GPU, berminggu-minggu → Model belajar "melihat dunia" ✅ Sudah dilakukan oleh Meta/Google ResNet-18 Pre-trained weights 11.7M parameters Tahu edges, shapes, textures torchvision.models.resnet18() TRANSFER! TASK ANDA 🔒 FROZEN: Conv Layers (Body) Sudah belajar dari 14M gambar — JANGAN diubah 🔓 TRAINABLE: FC Layer (Head) Ganti: 1000 kelas → KELAS ANDA (misal: 10 bunga) Hasil ❌ From scratch: ~20% akurasi (5 epoch) ✅ Transfer learning: ~96% akurasi (5 epoch) ⏱ Training time: Dari jam → menit 📊 Data needed: Dari jutaan → ratusan

💡 Analogi: Belajar Bahasa Baru

Bayangkan Anda sudah fasih Bahasa Inggris (= pre-trained model). Sekarang mau belajar Belanda. Anda tidak mulai dari nol — alfabet sama, grammar mirip, banyak kata serupa. Anda hanya perlu belajar perbedaannya. Itulah transfer learning: model sudah "fasih" mengenali edges, shapes, textures. Anda hanya perlu mengajarinya perbedaan antara bunga mawar dan bunga tulip.

🏗️

2. ResNet — Skip Connections yang Merevolusi DL

ResNet memungkinkan network sangat dalam (152 layers!) tanpa kehilangan gradient

🏗️ Residual Block — Rahasia Kedalaman ResNet

❌ Plain Network (Masalah) Conv + ReLU Conv + ReLU Output: F(x) Gradient menghilang di layer dalam! "Vanishing gradient problem" ✅ Residual Block (ResNet Solution) x Conv + ReLU Conv (no ReLU) Skip! + F(x) + x Gradient bisa "shortcut" via skip! Network bisa 152+ layers deep ✅
ModelLayersParamsImageNet Top-1SpeedBest For
ResNet-181811.7M69.8%🟢 Sangat cepatPrototype, data kecil, edge devices
ResNet-343421.8M73.3%🟢 CepatBalance speed + accuracy
ResNet-505025.6M76.1%🟡 MediumProduction, general purpose
ResNet-10110144.5M77.4%🟡 LambatAkurasi tinggi, GPU kuat
ResNet-15215260.2M78.3%🔴 Sangat lambatKompetisi, riset
EfficientNet-B0-5.3M77.1%🟢 EfisienMobile, edge, resource-limited

3. Dua Strategi Transfer Learning

Feature extraction (cepat, simpel) vs Fine-tuning (akurasi lebih tinggi)

⚡ Dua Strategi — Feature Extraction vs Fine-Tuning

Strategy A: Feature Extraction 🔒 Conv layers — FROZEN (tidak berubah) 🔓 FC head — TRAIN (baru, random) ✅ Cepat (menit) ✅ Data sedikit cukup ✅ Tidak butuh GPU kuat ✅ Low risk of overfitting ❌ Akurasi kadang terbatas → ~91-94% akurasi Strategy B: Fine-Tuning 🔒 Early layers — FROZEN 🔓 Later layers — TRAIN (lr kecil) 🔓 FC head — TRAIN (lr normal) ✅ Akurasi terbaik ✅ Model adaptasi penuh ❌ Lebih lambat ❌ Butuh lebih banyak data ❌ Risk overfitting lebih tinggi → ~96-98% akurasi
💻

4. Kode: Feature Extraction

Freeze semua, ganti kepala, train hanya FC layer
13_feature_extraction.py — Transfer Learning Strategy A
import torch import torch.nn as nn import torchvision from torchvision import models, transforms from torch.utils.data import DataLoader # =========================== # STEP 1: Load pre-trained ResNet-18 # =========================== model = models.resnet18(weights='IMAGENET1K_V1') # ↑ Download 44.7MB model yang sudah terlatih di ImageNet # Model ini SUDAH tahu: edges, textures, shapes, objects # =========================== # STEP 2: FREEZE semua layer (jangan diubah) # =========================== for param in model.parameters(): param.requires_grad = False # 🔒 Freeze! # =========================== # STEP 3: GANTI "kepala" (FC layer terakhir) # =========================== # ResNet-18 asli: fc = Linear(512, 1000) → 1000 kelas ImageNet # Kita ganti jadi: fc = Linear(512, 10) → 10 kelas kita num_features = model.fc.in_features # 512 model.fc = nn.Linear(num_features, 10) # 🔓 Layer baru (trainable!) # Hitung: berapa parameter yang akan di-train? trainable = sum(p.numel() for p in model.parameters() if p.requires_grad) total = sum(p.numel() for p in model.parameters()) print(f"Trainable: {trainable:,} / {total:,} ({100*trainable/total:.1f}%)") # Trainable: 5,130 / 11,181,642 (0.05%) # ↑ Hanya 0.05% parameter yang di-train! Sisanya frozen. # =========================== # STEP 4: Data transforms (resize ke 224×224 untuk ResNet) # =========================== transform = transforms.Compose([ transforms.Resize(256), transforms.CenterCrop(224), # ResNet expects 224×224 transforms.ToTensor(), transforms.Normalize( [0.485, 0.456, 0.406], # ImageNet mean (RGB) [0.229, 0.224, 0.225] # ImageNet std (RGB) ) ]) # =========================== # STEP 5: Optimizer — HANYA train FC parameters! # =========================== device = torch.device("cuda" if torch.cuda.is_available() else "cpu") model = model.to(device) optimizer = torch.optim.SGD( model.fc.parameters(), # ← HANYA fc layer! lr=0.001, momentum=0.9 ) loss_fn = nn.CrossEntropyLoss()
💡 Key Insight: Dari 11.1 juta parameter, kita hanya train 5.130 (0.05%)! Sisanya frozen — tetap menggunakan knowledge dari ImageNet. Ini mengapa feature extraction sangat cepat dan data-efficient.
🔧

5. Kode: Fine-Tuning (Akurasi Lebih Tinggi)

Unfreeze layer terakhir + train dengan learning rate berbeda
14_fine_tuning.py — Transfer Learning Strategy B
# =========================== # Fine-Tuning: Unfreeze layer terakhir # =========================== # Load pre-trained model model = models.resnet18(weights='IMAGENET1K_V1') # Freeze SEMUA dulu for param in model.parameters(): param.requires_grad = False # Unfreeze layer4 (layer terakhir sebelum FC) for param in model.layer4.parameters(): param.requires_grad = True # 🔓 Unfreeze! # Ganti FC head num_features = model.fc.in_features model.fc = nn.Linear(num_features, 10) # =========================== # Discriminative Learning Rates! # Layer dekat input → lr kecil (fitur dasar, jangan ubah banyak) # Layer dekat output → lr besar (perlu adaptasi ke task baru) # =========================== optimizer = torch.optim.Adam([ {'params': model.layer4.parameters(), 'lr': 1e-4}, # LR kecil {'params': model.fc.parameters(), 'lr': 1e-3}, # LR normal ]) # Learning rate scheduler: turunkan LR setiap 7 epoch scheduler = torch.optim.lr_scheduler.StepLR( optimizer, step_size=7, gamma=0.1 ) # Training loop (sama seperti biasa) for epoch in range(15): model.train() for images, labels in train_loader: images, labels = images.to(device), labels.to(device) pred = model(images) loss = loss_fn(pred, labels) optimizer.zero_grad() loss.backward() optimizer.step() scheduler.step() # Update LR # Feature Extraction: ~91-94% akurasi # Fine-Tuning: ~96-98% akurasi ← Jauh lebih baik!

🎓 Discriminative Learning Rates

Layer dekat input sudah belajar fitur universal (edges, gradients) — ini berlaku untuk semua gambar, jadi kita hanya perlu sedikit tweak (lr kecil: 0.0001). Layer dekat output belajar fitur spesifik (bentuk wajah, pola bunga) — ini perlu disesuaikan ke task baru (lr besar: 0.001). Pendekatan ini disebut discriminative learning rates dan memberikan hasil terbaik.

🔥

6. Grad-CAM: "Apa yang Dilihat Model?"

Visualisasi heatmap — area mana yang membuat model memutuskan prediksi

Grad-CAM (Gradient-weighted Class Activation Mapping) memvisualisasikan area mana di gambar yang paling mempengaruhi prediksi model. Ini penting untuk: memverifikasi model melihat hal yang benar, debugging kesalahan, dan menjelaskan keputusan AI.

🔥 Grad-CAM — Heatmap "Attention" Model

Input Gambar 🐱 "Kucing Persia" ResNet Prediksi 🐱 Cat: 94.2% 🐕 Dog: 3.1% 🐰 Rabbit: 1.4% TAPI... apa yang model "lihat"? 🤔 Grad-CAM Heatmap Overlay 🐱 🔴 Merah = area paling penting Interpretasi ✅ Model fokus ke: • Wajah kucing (mata, hidung) • Bentuk telinga • Kumis / whiskers → Model "melihat" hal yang benar untuk classify kucing → Prediksi bisa dipercaya! ✅ Low High
15_gradcam.py — Visualisasi Grad-CAM
# pip install pytorch-grad-cam from pytorch_grad_cam import GradCAM from pytorch_grad_cam.utils.image import show_cam_on_image # Target layer: layer terakhir sebelum FC cam = GradCAM( model=model, target_layers=[model.layer4[-1]] # Conv layer terakhir ) # Generate heatmap input_tensor = transform(image).unsqueeze(0).to(device) grayscale_cam = cam(input_tensor=input_tensor) # Overlay heatmap di atas gambar asli visualization = show_cam_on_image( rgb_image, # Gambar asli (numpy) grayscale_cam[0], # Heatmap use_rgb=True ) # Tampilkan import matplotlib.pyplot as plt plt.imshow(visualization) plt.title("Grad-CAM: Apa yang Dilihat Model?") plt.axis('off') plt.show()
🎯

7. Kapan Pakai Strategi Mana?

Decision framework berdasarkan ukuran data dan kemiripan domain
SituasiData AndaStrategiContoh
Data kecil, domain mirip100-1000 gambar, mirip ImageNetFeature ExtractionClassify anjing breeds, jenis mobil
Data besar, domain mirip10K+ gambar, mirip ImageNetFine-Tuning (unfreeze later layers)Product recognition, food classification
Data kecil, domain berbeda100-1000, sangat beda dari ImageNetFeature Extraction (hati-hati)X-ray medis, satellite imagery
Data besar, domain berbeda50K+, sangat bedaFine-Tuning (unfreeze banyak/semua)Microscopy, industrial defect
Real-time / edge deviceAnyEfficientNet / MobileNetMobile app, IoT camera, drone
⚠️ Aturan Emas: Selalu mulai dengan Feature Extraction dulu (cepat, murah, baseline). Jika akurasi belum cukup, baru naik ke Fine-Tuning. Jangan langsung unfreeze semua — mulai dari layer terakhir, evaluate, baru unfreeze lebih banyak jika perlu.
📝

8. Ringkasan Part 4

Konsep baru yang kita kuasai
KonsepApa ItuKode Kunci
Transfer LearningPinjam knowledge dari model pre-trainedmodels.resnet18(weights='IMAGENET1K_V1')
Freeze LayersMatikan gradient → layer tidak berubahparam.requires_grad = False
Replace HeadGanti FC layer terakhir untuk task barumodel.fc = nn.Linear(512, num_classes)
Feature ExtractionFreeze semua, train hanya head baruOptimizer: model.fc.parameters()
Fine-TuningUnfreeze sebagian layer + train bersamamodel.layer4.parameters() + model.fc
Discriminative LRLR berbeda per layer group[{'params': ..., 'lr': 1e-4}, ...]
LR SchedulerTurunkan LR otomatis setiap N epochStepLR(optimizer, step_size=7, gamma=0.1)
ResNet Skip ConnectionOutput = F(x) + x → gradient bisa shortcutBuilt-in di arsitektur ResNet
Grad-CAMHeatmap: area mana yang diperhatikan modelGradCAM(model, target_layers=[...])
ImageNet NormalizeMean/std khusus ImageNet (wajib untuk pre-trained)Normalize([.485,.456,.406],[.229,.224,.225])
🔥
Tech Review Desk — Seri Belajar PyTorch
Tutorial hands-on. Sumber: pytorch.org docs, PyTorch Foundation, PyImageSearch, KDnuggets, CodingNomads. PyTorch v2.7+ (2026).
📧 rominur@gmail.com  •  ✈️ t.me/Jekardah_AI — For collaboration & discussion