Tahap model pada rencana berjalan, dan ruang kerja kita mulai dipenuhi percobaan: regresi logistik dengan fitur kunjungan saja, ditambah umur keanggotaan, dengan ambang 0,5 lalu 0,4, di atas data versi Januari lalu versi Februari. Dua minggu kemudian laporan memuat satu angka recall terbaik — dan tidak ada yang ingat percobaan mana yang menghasilkannya, memakai data versi berapa, dengan ambang berapa. Bab ini menata kekacauan itu dengan satu disiplin: setiap eksperimen dicatat lengkap — nama, pengaturan, versi data, seed, hasil, dan keputusannya — sebelum kita melompat ke percobaan berikutnya. Pencatatan bukan pekerjaan tambahan setelah analisis; pencatatan adalah bagian dari eksperimen itu sendiri.

Apa yang Dicatat dari Setiap Eksperimen #

Sebuah eksperimen hanya bermakna bila ketiga unsurnya tercatat bersama: parameter (apa yang kita atur), data (versi mana yang dipakai), dan hasil (angka metrik yang keluar). Ketiganya harus hadir dalam satu baris catatan, karena hasil tanpa parameter tidak bisa diulang, dan parameter tanpa versi data bisa menuntun pada angka yang tidak bisa ditemukan kembali. Elemen keempat yang membedakan log yang hidup dari arsip: catatan keputusan — apa yang kita simpulkan dari angka itu.

Kolom logIsinyaKenapa wajib
namapengenal unik percobaanmemungkinkan satu baris dirujuk tanpa salah paham
pengaturanmodel, fitur, ambangmenentukan hasil; tanpa ini hasil tak bisa diulang
dataversi atau tanggal potret datahasil pada data berbeda bukan hasil yang sama
seedangka seed acakhasil acak hanya bisa direproduksi dengan seed yang sama
recallmetrik utama yang dibandingkanangka yang diperebutkan antar percobaan
catatankeputusan atau kejanggalanmengubah baris menjadi pengalaman yang bisa dibaca

Log Eksperimen dengan pandas #

Kita praktikkan dengan log proyek retensi Toko Kopi Kita: lima percobaan yang merekam jalan dari aturan sederhana sampai model terbaik, lalu ujinya pada data versi baru. Log disimpan sebagai DataFrame, dicetak, ditulis ke berkas CSV, dan dibaca kembali untuk memastikan catatan itu utuh — persis seperti riwayat eksperimen disimpan di proyek sungguhan.

python
import os

import pandas as pd

log_eksperimen = pd.DataFrame([
    {"nama": "aturan", "pengaturan": "ambang kunjungan < 5",
     "data": "v1 (31 Jan)", "seed": "-", "recall": 0.62,
     "catatan": "baseline tanpa model"},
    {"nama": "logistik_a", "pengaturan": "fitur: kunjungan",
     "data": "v1 (31 Jan)", "seed": 42, "recall": 0.71,
     "catatan": "unggul baseline"},
    {"nama": "logistik_b", "pengaturan": "fitur: kunjungan + umur",
     "data": "v1 (31 Jan)", "seed": 42, "recall": 0.74,
     "catatan": "umur membantu sedikit"},
    {"nama": "logistik_b_04", "pengaturan": "fitur sama, ambang 0.40",
     "data": "v1 (31 Jan)", "seed": 42, "recall": 0.79,
     "catatan": "precision turun ke 0.52"},
    {"nama": "logistik_b_v2", "pengaturan": "fitur sama, data baru",
     "data": "v2 (7 Feb)", "seed": 42, "recall": 0.69,
     "catatan": "turun di data baru - periksa pergeseran"},
])

print(log_eksperimen.to_string(index=False))

log_eksperimen.to_csv("eksperimen.csv", index=False)
baca_ulang = pd.read_csv("eksperimen.csv")
print()
print("tersimpan", len(baca_ulang), "eksperimen:",
      ", ".join(baca_ulang["nama"]))
os.remove("eksperimen.csv")

Output yang Dihasilkan:

text
         nama              pengaturan        data seed  recall                                 catatan
       aturan    ambang kunjungan < 5 v1 (31 Jan)    -    0.62                    baseline tanpa model
   logistik_a        fitur: kunjungan v1 (31 Jan)   42    0.71                         unggul baseline
   logistik_b fitur: kunjungan + umur v1 (31 Jan)   42    0.74                   umur membantu sedikit
logistik_b_04 fitur sama, ambang 0.40 v1 (31 Jan)   42    0.79                 precision turun ke 0.52
logistik_b_v2   fitur sama, data baru  v2 (7 Feb)   42    0.69 turun di data baru - periksa pergeseran

tersimpan 5 eksperimen: aturan, logistik_a, logistik_b, logistik_b_04, logistik_b_v2

Mari kita baca log tersebut:

  1. Baris demi baris menceritakan perkembangan: dari baseline 0,62, fitur umur menaikkan recall ke 0,74, dan penurunan ambang ke 0,40 memborong 0,79 dengan harga precision 0,52 — tukar yang satu kita bayar dengan yang lain, dan catatannya jujur soal itu.
  2. Kolom data menyelamatkan baris terakhir dari penafsiran keliru: recall 0,69 pada logistik_b_v2 bukan kemunduran model, melainkan hasil pada potret data yang lebih baru. Tanpa kolom ini, dua angka yang tidak sebanding akan dibandingkan juga.
  3. to_csv() lalu read_csv() menegaskan bahwa log bertahan melewati sesi kerja — catatan eksperimen yang hanya hidup di memori hilang begitu kernel dimatikan. Pada proyek sungguhan berkas eksperimen.csv disimpan di repositori dan dilacak Git, bukan dihapus; os.remove() di sini hanya menjaga folder contoh tetap bersih.
  4. Kolom catatan mengubah data menjadi keputusan: baris terakhir bukan sekadar angka, melainkan perintah lanjutan — “periksa pergeseran” — yang menghubungkannya dengan pemantauan drift yang sudah kita kenal di chapter Drift Detection .

Dari Log CSV ke MLflow #

Log DataFrame dan CSV memadai untuk proyek kecil, tetapi tiga kebutuhan yang lebih besar menuntut alat khusus: jumlah percobaan yang banyak, pembandingan yang nyaman, dan rekan tim yang ikut mencatat. Di sanalah MLflow masuk — pustaka pelacakan eksperimen yang menjalankan konsep yang sama persis dengan log kita, hanya lebih rapi. Setiap percobaan menjadi sebuah run; kita mencatat parameter lewat mlflow.log_param(), metrik lewat mlflow.log_metric(), dan berkas keluaran lewat mlflow.log_artifact(); antarmuka MLflow lalu menyajikan seluruh run dalam tabel yang bisa disaring dan dibandingkan, lengkap dengan grafik perbandingan metrik.

KebutuhanLog CSVMLflow
Belasan percobaan, satu orangmemadai — satu berkas, mudah dibacaberlebihan
Ratusan percobaan, banyak modeltabel melebar dan sulit disaringpenyaringan dan pengurutan bawaan
Perbandingan visual antar percobaankita gambar sendiritersedia di antarmuka pelacakan
Rekan tim mencatat bersamaanrisiko saling menimpa berkassetiap run terpisah otomatis

Prinsipnya jangan berubah saat alatnya berganti: parameter, data, seed, hasil, dan keputusan tetap dicatat setiap kali — MLflow hanya memindahkan tempat catatan itu disimpan dan membantu membacanya. Dokumentasi resmi MLflow memuat panduan pelacakan yang lengkap, dari pemasangan sampai penataan eksperimen.

Rangkuman #

  • Eksperimen hanya bermakna bila parameter, versi data, dan hasilnya tercatat bersama dalam satu baris; hasil tanpa parameter tidak bisa diulang.
  • Kolom catatan mengubah log dari arsip angka menjadi pengalaman yang bisa dibaca: keputusan dan kejanggalan ikut tertulis.
  • Versi data pada setiap baris mencegah perbandingan antar angka yang tidak sebanding — hasil pada potret data berbeda adalah hasil yang berbeda.
  • Log DataFrame/CSV memadai untuk proyek kecil; MLflow meladeni skala besar dengan run terpisah, penyaringan, dan antarmuka pembandingan, dengan prinsip pencatatan yang sama.
  • Eksperimen yang gagal pun dicatat — pengetahuan tentang jalan buntu sama berharganya dengan jalan yang berhasil.

Eksperimen kita kini meninggalkan jejak yang rapi. Namun setiap eksperimen itu bermuara ke satu benda yang sering luput dari perhatian: dataset itu sendiri. Enam bulan dari sekarang, adakah orang lain yang bisa memuat data transaksi kita dan memahami arti setiap kolomnya tanpa menebak? Itu pekerjaan dokumentasi — pembahasan chapter berikutnya: Dokumentasi Dataset .

Referensi #

  1. MLflow — Documentation
  2. pandas — User Guide