تقسيم البيانات: تدريب واختبار
لماذا نخفي خُمس البيانات عن النموذج، وكيف نقسّمها بعدل؟ ⏱ نحو 40 دقيقة.
- تدرك خطورة الاختبار على بيانات التدريب.
- تقسّم البيانات بـ
train_test_split. - تثبّت التقسيم بـ
random_state. - تحافظ على توازن الفئات بـ
stratify.
١لماذا نخفي جزءًا من البيانات؟
لو درّبت النموذج على كل بياناتك ثم اختبرته عليها نفسها، لكان كطالبٍ يرى أسئلة الاختبار قبله: درجةٌ عالية مزيّفة. الحلّ: قسّم البيانات — جزءٌ للتدريب (يتعلّم منه)، وجزءٌ للاختبار (لم يره، نقيس عليه صدق التنبؤ).
٢train_test_split
scikit-learn يقسّم بسطرٍ واحد. المعتاد 80% تدريبًا و20% اختبارًا، مع random_state لتثبيت التقسيم (تكراريّة):
import pandas as pdfrom sklearn.model_selection import train_test_split df = pd.DataFrame({ "seconds": [8, 120, 5, 240, 40, 180, 60, 300, 15, 90], "pages": [1, 4, 1, 6, 2, 5, 3, 9, 1, 4], "bought": [0, 1, 0, 1, 0, 1, 0, 1, 0, 1],})X = df[["seconds", "pages"]]y = df["bought"] X_train, X_test, y_train, y_test = train_test_split( X, y, test_size=0.2, random_state=42) print("تدريب:", len(X_train), "| اختبار:", len(X_test))
random_state=42 يضمن أن كل تشغيلٍ يعطي التقسيم نفسه، فتتكرّر نتائجك. أيّ رقمٍ ثابت يصلح؛ المهمّ ثباته.
٣التوازن في التصنيف: stratify
في التصنيف، إن كانت الفئات غير متوازنة (95% لم يشتروا)، قد يقع كل المشترين في جانبٍ واحد صدفةً. stratify=y يحافظ على نسبة الفئات في الجزأين:
import pandas as pdfrom sklearn.model_selection import train_test_split df = pd.DataFrame({ "x": list(range(10)), "y": [0,0,0,0,0,0,0,0,1,1], # فئتان غير متوازنتين})Xtr, Xte, ytr, yte = train_test_split( df[["x"]], df["y"], test_size=0.4, random_state=0, stratify=df["y"])print("نسبة الفئة 1 في التدريب:", round(ytr.mean(), 2))print("نسبة الفئة 1 في الاختبار:", round(yte.mean(), 2))
توقّع وتحقّق
لماذا نقسّم البيانات؟
دالة التقسيم:
random_state يضمن:
للحفاظ على نسبة الفئات:
الخلاصة
- النموذج يُقيَّم على بياناتٍ لم يرها؛ لذا نقسّم تدريبًا واختبارًا.
train_test_splitيقسّم بسطر؛ المعتاد80/20.random_stateيثبّت التقسيم فتتكرّر النتائج.stratifyيحافظ على نسبة الفئات مع البيانات غير المتوازنة.
تحدٍّ برمجي: قسّم البيانات
متوسطقسّم البيانات 80/20 بـ random_state=42، واطبع حجم التدريب ثم حجم الاختبار.
- استخدم
train_test_split(..., test_size=0.2, random_state=42). - اطبع
len(X_train)ثمlen(X_test).
ابدأ من هذا الكود، واضغط ▶ شغّل هنا لتكتب حلّك وتجرّبه مباشرة:
import pandas as pdfrom sklearn.model_selection import train_test_splitdf = pd.DataFrame({ "a": list(range(20)), "b": list(range(20, 40)), "y": [0,1]*10,})X = df[["a", "b"]]; y = df["y"]# قسّم 80/20 (random_state=42) واطبع حجم التدريب ثم الاختبار
💡 تلميح 1
train_test_split(X, y, test_size=0.2, random_state=42).💡 تلميح 2
len(X_train) وlen(X_test).حاول بنفسك أولًا؛ للمسألة أكثر من حلّ صحيح.
import pandas as pdfrom sklearn.model_selection import train_test_splitdf = pd.DataFrame({ "a": list(range(20)), "b": list(range(20, 40)), "y": [0,1]*10,})X = df[["a", "b"]]; y = df["y"]X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=42)print(len(X_train))print(len(X_test))