Baza (baseline) va birinchi model
Sahna: 0.85 — bu yaxshimi?
Talabangiz yugurib keladi: "Ustoz, modelim 85% aniqlik berdi!"
Siz bitta savol berasiz: "Ma'lumotingizda nechta foiz 'ha' bor?"
U bilmaydi.
Agar javob 85% bo'lsa — uning modeli hech narsa o'rganmagan. "Hammaga ha" deydigan model ham xuddi shuncha beradi.
Bu bob bitta raqam haqida: chegara. 0-bobdagi protokolning 6-qadami.
Termometrsiz "issiq" so'zi ma'nosiz
accuracy = 0.85 — bu o'z-o'zidan hech narsa anglatmaydi. U faqat taqqoslashda ma'noga ega.
Nimaga taqqoslaymiz? Hech narsa o'rganmaydigan eng ahmoq modelga.
Agar siz undan oshmasangiz — sizning murakkab modelingiz, ikki haftalik ishingiz, GPU vaqtingiz behuda ketgan.
import pandas as pd from sklearn.model_selection import train_test_split from sklearn.dummy import DummyClassifier from sklearn.metrics import accuracy_score, f1_score df = pd.read_csv(DATA / "uy_ijara.csv") son = ["xonalar", "maydon_m2", "qavat", "qavatlar_soni", "metro_km", "mebel", "qurilgan_yil"] X, y = df[son + ["tuman"]], df["ijaraga_berildi_30k"] X_tr, X_te, y_tr, y_te = train_test_split(X, y, test_size=0.3, random_state=42, stratify=y) print(f"Target nisbati: {y.mean():.1%} 'ha'")
Target nisbati: 50.7% 'ha'
DummyClassifier — to'rtta ahmoq model
sklearn da tayyor. Har xil "ahmoqlik" turi bor.
strategiyalar = { "most_frequent": "Har doim eng ko'p uchraydigan sinfni aytadi", "stratified": "Sinf nisbatiga qarab tasodifiy aytadi", "uniform": "Tanga tashlaydi (teng ehtimol)", "prior": "most_frequent bilan bir xil bashorat qiladi", } qatorlar = [] for s, izoh in strategiyalar.items(): d = DummyClassifier(strategy=s, random_state=42).fit(X_tr[son], y_tr) b = d.predict(X_te[son]) qatorlar.append({"Strategiya": s, "Accuracy": round(accuracy_score(y_te, b), 4), "F1": round(f1_score(y_te, b, zero_division=0), 4), "Nima qiladi": izoh}) show(pd.DataFrame(qatorlar))
| Strategiya | Accuracy | F1 | Nima qiladi |
|---|---|---|---|
| most_frequent | 0.506 | 0.672 | Har doim eng ko'p uchraydigan sinfni aytadi |
| stratified | 0.494 | 0.494 | Sinf nisbatiga qarab tasodifiy aytadi |
| uniform | 0.522 | 0.525 | Tanga tashlaydi (teng ehtimol) |
| prior | 0.506 | 0.672 | most_frequent bilan bir xil bashorat qiladi |
Qaysi birini olamiz? most_frequent — chunki u eng "kuchli ahmoq". Boshqa strategiyalar undan past bo'ladi, shuning uchun eng qattiq chegarani u beradi.
baza = accuracy_score(y_te, DummyClassifier(strategy="most_frequent") .fit(X_tr[son], y_tr).predict(X_te[son])) print(f"BAZA = {baza:.4f}") print() print("Shu raqamni daftaringizga yozing. Har bir keyingi natija shunga taqqoslanadi.")
BAZA = 0.5056 Shu raqamni daftaringizga yozing. Har bir keyingi natija shunga taqqoslanadi.
Endi haqiqiy model
from sklearn.pipeline import Pipeline from sklearn.compose import ColumnTransformer from sklearn.preprocessing import StandardScaler, OneHotEncoder from sklearn.impute import SimpleImputer from sklearn.linear_model import LogisticRegression quvur = Pipeline([ ("tayyorla", ColumnTransformer([ ("son", Pipeline([("toldir", SimpleImputer(strategy="median")), ("shkala", StandardScaler())]), son), ("matn", OneHotEncoder(handle_unknown="ignore"), ["tuman"]), ])), ("model", LogisticRegression(max_iter=2000)), ]).fit(X_tr, y_tr) model_acc = accuracy_score(y_te, quvur.predict(X_te)) print(f"BAZA : {baza:.4f}") print(f"MODEL : {model_acc:.4f}") print(f"Farq : {model_acc - baza:+.4f}") print() print("Hukm:", "O'TDI — model haqiqatan o'rgandi" if model_acc > baza + 0.02 else "O'TMADI")
BAZA : 0.5056 MODEL : 0.7778 Farq : +0.2722 Hukm: O'TDI — model haqiqatan o'rgandi
Nomutanosib ma'lumotda baza sizni aldaydi
Yuqorida target 50/50 edi, shuning uchun baza past (0.5) va modelni o'tish oson.
Endi boshqa datasetga qaraymiz — talaba bitirishi.
td = pd.read_csv(DATA / "talaba_bitirdi.csv", keep_default_na=False, na_values=[""]) th = ["kirish_bali", "davomat_foiz", "uy_vazifa_bali", "ishlaydi", "masofa_km"] Xt, yt = td[th], td["bitirdi"] Xt_tr, Xt_te, yt_tr, yt_te = train_test_split(Xt, yt, test_size=0.3, random_state=42, stratify=yt) baza_t = accuracy_score(yt_te, DummyClassifier(strategy="most_frequent") .fit(Xt_tr, yt_tr).predict(Xt_te)) model_t = LogisticRegression(max_iter=2000).fit(Xt_tr, yt_tr) acc_t = accuracy_score(yt_te, model_t.predict(Xt_te)) print(f"Target nisbati : {yt.mean():.1%} bitirgan") print(f"BAZA : {baza_t:.4f}") print(f"MODEL : {acc_t:.4f}") print(f"Farq : {acc_t - baza_t:+.4f}")
Target nisbati : 88.6% bitirgan BAZA : 0.8852 MODEL : 0.8963 Farq : +0.0111
Mana bu — talabangiz tushadigan tuzoq.
Model 0.8963 beradi. "Deyarli 90 foiz!" deb hisobotga yozish mumkin. Lekin baza 0.8852 — ya'ni modelning butun qo'shgan hissasi 0.011, ya'ni 270 qatordan uchtasi.
Baza yuqori bo'lsa, accuracy ni tashlang
Agar baza 0.85 dan yuqori bo'lsa, accuracy ni o'lchov sifatida ishlatish deyarli ma'nosiz. Chunki shovqin ham shu darajada bo'ladi.
Nima qilish kerak: F1, recall yoki PR-AUC ga o'tish. 8-bob shu haqda.
print("Xuddi shu model, boshqa metrikalar bilan:") b = model_t.predict(Xt_te) print(f" Accuracy : {accuracy_score(yt_te, b):.4f} (baza {baza_t:.4f} — foydasi kam)") print(f" F1 : {f1_score(yt_te, b):.4f}") from sklearn.metrics import recall_score, precision_score print(f" Precision: {precision_score(yt_te, b, zero_division=0):.4f}") print(f" Recall : {recall_score(yt_te, b, zero_division=0):.4f}")
Xuddi shu model, boshqa metrikalar bilan: Accuracy : 0.8963 (baza 0.8852 — foydasi kam) F1 : 0.9447 Precision: 0.8951 Recall : 1.0000
Regression da baza
Regression uchun DummyRegressor bor. U har doim o'rtachani (yoki medianani) aytadi.
from sklearn.dummy import DummyRegressor from sklearn.linear_model import Ridge from sklearn.metrics import root_mean_squared_error, r2_score yn = df["narx_usd"] Xn_tr, Xn_te, yn_tr, yn_te = train_test_split(X, yn, test_size=0.3, random_state=42) d_reg = DummyRegressor(strategy="mean").fit(Xn_tr[son], yn_tr) rmse_baza = root_mean_squared_error(yn_te, d_reg.predict(Xn_te[son])) quvur_reg = Pipeline([ ("tayyorla", ColumnTransformer([ ("son", Pipeline([("toldir", SimpleImputer(strategy="median")), ("shkala", StandardScaler())]), son), ("matn", OneHotEncoder(handle_unknown="ignore"), ["tuman"]), ])), ("model", Ridge()), ]).fit(Xn_tr, yn_tr) bashorat_reg = quvur_reg.predict(Xn_te) print(f"BAZA (har doim o'rtacha): RMSE = {rmse_baza:.1f} R2 = {r2_score(yn_te, d_reg.predict(Xn_te[son])):.4f}") print(f"MODEL (Ridge) : RMSE = {root_mean_squared_error(yn_te, bashorat_reg):.1f} R2 = {r2_score(yn_te, bashorat_reg):.4f}")
BAZA (har doim o'rtacha): RMSE = 228.6 R2 = -0.0044 MODEL (Ridge) : RMSE = 71.2 R2 = 0.9025
R2 ning o'zi bazani ichiga olgan
R2 = 0 degani — "o'rtachani aytgan bilan bir xil". R2 < 0 — "o'rtachadan ham yomon".
Shuning uchun regression da R2 allaqachon bazaga nisbatan o'lchaydi. Lekin RMSE ni baza bilan taqqoslash foydali: u sizga qancha yaxshilandi degan savolga biznes tilida javob beradi.
Biznes bazasi — eng muhimi
Dummy model — statistik baza. Lekin haqiqiy loyihada uchinchi baza bor va u eng muhimi:
Hozir bu ishni kim/nima qilyapti?
Agentlikda tajribali xodim "bu kvartira tez ketadi" deb taxmin qiladi va u 70% to'g'ri chiqadi. Sizning modelingiz 0.7778 beradi.
Statistik bazadan (0.5056) siz ancha o'tdingiz. Lekin biznes bazasidan (0.70) — atigi 0.08. Menejer uchun muhim raqam shu ikkinchisi.
show(pd.DataFrame([ {"Baza turi": "Dummy (most_frequent)", "Nimani ko'rsatadi": "Model umuman o'rganganmi", "Kim so'raydi": "Siz"}, {"Baza turi": "Oddiy qoida (if narx < X)", "Nimani ko'rsatadi": "ML murakkabligi kerakmi", "Kim so'raydi": "Senior muhandis"}, {"Baza turi": "Hozirgi jarayon (odam/eski tizim)", "Nimani ko'rsatadi": "Loyiha foyda keltiradimi", "Kim so'raydi": "Menejer — eng muhim savol"}, ]))
| Baza turi | Nimani ko'rsatadi | Kim so'raydi |
|---|---|---|
| Dummy (most_frequent) | Model umuman o'rganganmi | Siz |
| Oddiy qoida (if narx < X) | ML murakkabligi kerakmi | Senior muhandis |
| Hozirgi jarayon (odam/eski tizim) | Loyiha foyda keltiradimi | Menejer — eng muhim savol |
Oddiy qoidani ham sinab ko'ramiz — ba'zan u ML ni ortiqcha qilib qo'yadi.
import numpy as np chegara = X_tr["maydon_m2"].median() qoida = (X_te["maydon_m2"] < chegara).astype(int) # kichik kvartira tezroq ketadi degan taxmin print(f"Qoida: maydon < {chegara:.0f} m2 bo'lsa 'tez ketadi'") print(f" Accuracy: {accuracy_score(y_te, qoida):.4f}") print(f" F1 : {f1_score(y_te, qoida, zero_division=0):.4f}") print() print(f"Taqqoslash -> dummy {baza:.4f} | qoida {accuracy_score(y_te, qoida):.4f} | model {model_acc:.4f}")
Qoida: maydon < 55 m2 bo'lsa 'tez ketadi' Accuracy: 0.7694 F1 : 0.7701 Taqqoslash -> dummy 0.5056 | qoida 0.7694 | model 0.7778
Bugun nima o'rgandik
show(pd.DataFrame([ {"Tushuncha": "Baza nima uchun", "Bitta jumla": "Busiz accuracy raqami ma'nosiz"}, {"Tushuncha": "DummyClassifier", "Bitta jumla": "most_frequent — eng qattiq chegara"}, {"Tushuncha": "DummyRegressor", "Bitta jumla": "Har doim o'rtacha; R2=0 shu nuqta"}, {"Tushuncha": "Yuqori baza", "Bitta jumla": "0.85 dan oshsa accuracy ni tashlab F1 ga o't"}, {"Tushuncha": "Oddiy qoida bazasi", "Bitta jumla": "ML umuman kerakmi degan savolga javob"}, {"Tushuncha": "Biznes bazasi", "Bitta jumla": "Hozir buni kim qilyapti va qanchalik yaxshi"}, ]))
| Tushuncha | Bitta jumla |
|---|---|
| Baza nima uchun | Busiz accuracy raqami ma'nosiz |
| DummyClassifier | most_frequent — eng qattiq chegara |
| DummyRegressor | Har doim o'rtacha; R2=0 shu nuqta |
| Yuqori baza | 0.85 dan oshsa accuracy ni tashlab F1 ga o't |
| Oddiy qoida bazasi | ML umuman kerakmi degan savolga javob |
| Biznes bazasi | Hozir buni kim qilyapti va qanchalik yaxshi |
Keyingi bobda: model bitta chegarada (threshold 0.5) ishlaydi. Uni surib, modelni qayta o'qitmasdan precision bilan recall o'rtasida tanlov qilamiz.
Bu bobni bepul o'qidingiz.
Kitob o'rgatadi, lekin sizning kodingiz nega ishlamaganini ayta olmaydi. Kursda uy vazifangiz tekshiriladi.