Notebook Bab 5 ini punya dua bagian. Bagian Demo tinggal Anda jalankan lalu amati keluarannya; bagian Mini Project berisi soal dan data yang Anda kerjakan sendiri.
Penanganan nilai hilang dibuat reproducible dengan menaruh imputasi sebagai transformer di dalam pipeline , bukan suntingan manual. Saat fitur berkorelasi, imputasi berbasis model memanfaatkan kolom lain untuk menebak nilai yang hilang.
Persiapan
import numpy as np
from sklearn.experimental import enable_iterative_imputer # noqa: F401
from sklearn.impute import SimpleImputer, IterativeImputer, KNNImputer
from sklearn.preprocessing import StandardScaler
from sklearn.pipeline import Pipeline
from sklearn.linear_model import Ridge
from sklearn.model_selection import cross_val_score
RANDOM_STATE = 42
rng = np.random.default_rng(RANDOM_STATE)
print ('Setup selesai.' )
Section 1 - Demo: Imputasi Reproducible di Dalam Pipeline
Data: fitur berkorelasi dengan nilai hilang
Enam fitur dibangun dari dua faktor laten (z1, z2), jadi tiap kelompok fitur saling berkorelasi kuat. Sekitar 25 persen sel dikosongkan secara acak.
n = 1200
z1 = rng.normal(size= n)
z2 = rng.normal(size= n)
X = np.column_stack([
z1 + 0.10 * rng.normal(size= n),
z1 + 0.10 * rng.normal(size= n),
z1 + 0.10 * rng.normal(size= n),
z2 + 0.10 * rng.normal(size= n),
z2 + 0.10 * rng.normal(size= n),
z2 + 0.10 * rng.normal(size= n),
])
y = 3.0 * z1 - 2.0 * z2 + rng.normal(scale= 0.5 , size= n)
Xmiss = X.copy()
Xmiss[rng.random(X.shape) < 0.25 ] = np.nan
print ('Bentuk data:' , Xmiss.shape, '| nilai hilang:' , int (np.isnan(Xmiss).sum ()))
Bentuk data: (1200, 6) | nilai hilang: 1823
Bandingkan tiga strategi imputasi
Semua di dalam pipeline (imputasi + StandardScaler + Ridge), jadi parameter imputasi di-fit ulang pada tiap fold latih saja.
def eval_imp(imputer):
pipe = Pipeline([('imp' , imputer), ('sc' , StandardScaler()), ('m' , Ridge())])
return cross_val_score(pipe, Xmiss, y, cv= 5 , scoring= 'r2' ).mean()
r_median = eval_imp(SimpleImputer(strategy= 'median' ))
r_knn = eval_imp(KNNImputer(n_neighbors= 5 ))
r_iter = eval_imp(IterativeImputer(random_state= RANDOM_STATE, max_iter= 10 ))
print (f'Median imputation : R2 = { r_median:.3f} ' )
print (f'KNN imputation : R2 = { r_knn:.3f} ' )
print (f'Iterative imputation : R2 = { r_iter:.3f} ' )
Median imputation : R2 = 0.875
KNN imputation : R2 = 0.895
Iterative imputation : R2 = 0.957
🔎 Amati. Karena tiap kelompok fitur berasal dari faktor laten yang sama, imputasi berbasis model (KNN dan Iterative) menebak nilai hilang dari kolom sekelompoknya dan mengungguli median per-kolom yang mengabaikan korelasi. Untuk data ber-outlier , ganti StandardScaler dengan RobustScaler (median dan IQR). Semua langkah di dalam pipeline , jadi parameter imputasi di-fit hanya pada data latih.
Soal
Anda diberi data numerik yang mengandung nilai hilang dan outlier . Targetnya nilai (regresi).
Tugas:
Bangun pipeline reproducible: imputasi + penanganan outlier (RobustScaler) + model.
Tambahkan missing-indicator (SimpleImputer(add_indicator=True)) dan cek apakah menaikkan skor.
Laporkan R2 dengan cross-validation .
Luaran: kode pipeline , R2 CV dengan dan tanpa missing-indicator , plus 2-3 kalimat analisis.
Kriteria penilaian: (a) seluruh transformasi di dalam pipeline ; (b) penanganan outlier eksplisit; (c) evaluasi memakai cross-validation .
# DATA AWAL (jangan diubah) - fitur berkorelasi dengan nilai hilang dan outlier.
m = 900
g1 = np.random.default_rng(11 ).normal(size= m)
g2 = np.random.default_rng(22 ).normal(size= m)
eps = np.random.default_rng(33 )
Xp = np.column_stack([
g1 + 0.15 * eps.normal(size= m),
g1 + 0.15 * eps.normal(size= m),
g2 + 0.15 * eps.normal(size= m),
g2 + 0.15 * eps.normal(size= m),
eps.normal(size= m),
])
yp = 2.5 * g1 - 1.5 * g2 + eps.normal(scale= 0.6 , size= m)
Xp[np.random.default_rng(44 ).random(Xp.shape) < 0.01 ] *= 8 # outlier
Xp[np.random.default_rng(55 ).random(Xp.shape) < 0.20 ] = np.nan # nilai hilang
print ('Data:' , Xp.shape, '| nilai hilang:' , int (np.isnan(Xp).sum ()))
Data: (900, 5) | nilai hilang: 863
# Kerjakan di sini.
# Petunjuk: Pipeline([('imp', SimpleImputer(add_indicator=True)), ('sc', RobustScaler()), ('m', Ridge())]).