.. DO NOT EDIT. .. THIS FILE WAS AUTOMATICALLY GENERATED BY SPHINX-GALLERY. .. TO MAKE CHANGES, EDIT THE SOURCE PYTHON FILE: .. "auto_examples/linear_model/plot_poisson_regression_non_normal_loss.py" .. LINE NUMBERS ARE GIVEN BELOW. .. only:: html .. note:: :class: sphx-glr-download-link-note :ref:`Go to the end ` to download the full example code. or to run this example in your browser via JupyterLite or Binder .. rst-class:: sphx-glr-example-title .. _sphx_glr_auto_examples_linear_model_plot_poisson_regression_non_normal_loss.py: ====================================== انحدار بواسون والخسارة غير الطبيعية ====================================== يوضح هذا المثال استخدام الانحدار اللوغاريتمي الخطي بواسون على `مجموعة بيانات مطالبات المسؤولية الطرفية الثالثة للسيارات الفرنسية `_ من [1]_ ويقارنها بنموذج خطي يتم تركيبه باستخدام خطأ المربعات الأقل المعتاد ونموذج GBRT غير خطي يتم تركيبه باستخدام خسارة بواسون (ورابط تسجيل الدخول). بعض التعريفات: - **السياسة** هي عقد بين شركة تأمين وفرد: **حامل الوثيقة، أي سائق السيارة في هذه الحالة. - **المطالبة** هي الطلب الذي يقدمه حامل الوثيقة إلى شركة التأمين لتعويضه عن خسارة مغطاة بالتأمين. - **التعرض** هو مدة تغطية التأمين لسياسة معينة، بالسنوات. - **تكرار المطالبات** هو عدد المطالبات مقسومًا على التعرض، يتم قياسه عادةً بعدد المطالبات في السنة. في هذه المجموعة من البيانات، يتوافق كل عينة مع سياسة تأمين. تتضمن الميزات المتوفرة عمر السائق وعمر المركبة وقوة المركبة، إلخ. هدفنا هو التنبؤ بالتردد المتوقع للمطالبات بعد حوادث السيارات لحامل وثيقة تأمين جديدة بالنظر إلى البيانات التاريخية على سكان حاملي وثائق التأمين. .. [1] A. Noll, R. Salzmann and M.V. Wuthrich, Case Study: French Motor Third-Party Liability Claims (November 8, 2018). `doi:10.2139/ssrn.3164764 `_ .. GENERATED FROM PYTHON SOURCE LINES 41-46 .. code-block:: Python import matplotlib.pyplot as plt import numpy as np import pandas as pd .. GENERATED FROM PYTHON SOURCE LINES 47-52 مجموعة بيانات مطالبات السيارات الفرنسية ----------------------------------------------------- دعنا نحمل مجموعة بيانات المطالبات من OpenML: https://www.openml.org/d/41214 .. GENERATED FROM PYTHON SOURCE LINES 52-57 .. code-block:: Python from sklearn.datasets import fetch_openml df = fetch_openml(data_id=41214, as_frame=True).frame df .. raw:: html
IDpol ClaimNb Exposure Area VehPower VehAge DrivAge BonusMalus VehBrand VehGas Density Region
0 1.0 1 0.10000 D 5 0 55 50 B12 'Regular' 1217 R82
1 3.0 1 0.77000 D 5 0 55 50 B12 'Regular' 1217 R82
2 5.0 1 0.75000 B 6 2 52 50 B12 'Diesel' 54 R22
3 10.0 1 0.09000 B 7 0 46 50 B12 'Diesel' 76 R72
4 11.0 1 0.84000 B 7 0 46 50 B12 'Diesel' 76 R72
... ... ... ... ... ... ... ... ... ... ... ... ...
678008 6114326.0 0 0.00274 E 4 0 54 50 B12 'Regular' 3317 R93
678009 6114327.0 0 0.00274 E 4 0 41 95 B12 'Regular' 9850 R11
678010 6114328.0 0 0.00274 D 6 2 45 50 B12 'Diesel' 1323 R82
678011 6114329.0 0 0.00274 B 4 0 60 50 B12 'Regular' 95 R26
678012 6114330.0 0 0.00274 B 7 6 29 54 B12 'Diesel' 65 R72

678013 rows × 12 columns



.. GENERATED FROM PYTHON SOURCE LINES 58-66 عدد المطالبات (``ClaimNb``) هو عدد صحيح إيجابي يمكن نمذجته كتوزيع بواسون. يفترض بعد ذلك أن يكون عدد الأحداث المنفصلة التي تحدث بمعدل ثابت في فترة زمنية معينة (``Exposure``، بوحدات السنوات). هنا نريد نمذجة التردد ``y = ClaimNb / Exposure`` شرطياً على ``X`` عبر توزيع بواسون (مقياس)، واستخدام ``Exposure`` كـ ``sample_weight``. .. GENERATED FROM PYTHON SOURCE LINES 66-83 .. code-block:: Python df["Frequency"] = df["ClaimNb"] / df["Exposure"] print("متوسط التردد = {}".format(np.average(df["Frequency"], weights=df["Exposure"]))) print("نسبة التعرض بدون مطالبات = {0:.1%}".format( df.loc[df["ClaimNb"] == 0, "Exposure"].sum() / df["Exposure"].sum() )) fig, (ax0, ax1, ax2) = plt.subplots(ncols=3, figsize=(16, 4)) ax0.set_title("عدد المطالبات") _ = df["ClaimNb"].hist(bins=30, log=True, ax=ax0) ax1.set_title("التعرض بالسنوات") _ = df["Exposure"].hist(bins=30, log=True, ax=ax1) ax2.set_title("التردد (عدد المطالبات في السنة)") _ = df["Frequency"].hist(bins=30, log=True, ax=ax2) .. image-sg:: /auto_examples/linear_model/images/sphx_glr_plot_poisson_regression_non_normal_loss_001.png :alt: عدد المطالبات, التعرض بالسنوات, التردد (عدد المطالبات في السنة) :srcset: /auto_examples/linear_model/images/sphx_glr_plot_poisson_regression_non_normal_loss_001.png :class: sphx-glr-single-img .. rst-class:: sphx-glr-script-out .. code-block:: none متوسط التردد = 0.10070308464041304 نسبة التعرض بدون مطالبات = 93.9% .. GENERATED FROM PYTHON SOURCE LINES 84-90 يمكن استخدام الأعمدة المتبقية للتنبؤ بتردد أحداث المطالبات. هذه الأعمدة غير متجانسة للغاية مع مزيج من المتغيرات الفئوية والرقمية بمقاييس مختلفة، ربما موزعة بشكل غير متساوٍ للغاية. من أجل تركيب نماذج خطية مع هذه المتنبئات، من الضروري لذلك من الضروري إجراء تحويلات ميزات قياسية كما يلي: .. GENERATED FROM PYTHON SOURCE LINES 90-122 .. code-block:: Python from sklearn.compose import ColumnTransformer from sklearn.pipeline import make_pipeline from sklearn.preprocessing import ( FunctionTransformer, KBinsDiscretizer, OneHotEncoder, StandardScaler, ) log_scale_transformer = make_pipeline( FunctionTransformer(np.log, validate=False), StandardScaler() ) linear_model_preprocessor = ColumnTransformer( [ ("passthrough_numeric", "passthrough", ["BonusMalus"]), ( "binned_numeric", KBinsDiscretizer(n_bins=10, random_state=0), ["VehAge", "DrivAge"], ), ("log_scaled_numeric", log_scale_transformer, ["Density"]), ( "onehot_categorical", OneHotEncoder(), ["VehBrand", "VehPower", "VehGas", "Region", "Area"], ), ], remainder="drop", ) .. GENERATED FROM PYTHON SOURCE LINES 123-134 خط أساس تنبؤ ثابت ------------------------------ تجدر الإشارة إلى أن أكثر من 93% من حاملي وثائق التأمين ليس لديهم مطالبات. إذا كنا سنحول هذه المشكلة إلى مهمة تصنيف ثنائي، فستكون غير متوازن بشكل كبير، وحتى نموذج بسيط يتنبأ فقط يمكن أن يحقق متوسط دقة 93%. لتقييم ملاءمة المقاييس المستخدمة، سننظر في خط أساس "غبي" مقدر يتنبأ باستمرار بمتوسط تردد عينة التدريب. .. GENERATED FROM PYTHON SOURCE LINES 134-149 .. code-block:: Python from sklearn.dummy import DummyRegressor from sklearn.model_selection import train_test_split from sklearn.pipeline import Pipeline df_train, df_test = train_test_split(df, test_size=0.33, random_state=0) dummy = Pipeline( [ ("preprocessor", linear_model_preprocessor), ("regressor", DummyRegressor(strategy="mean")), ] ).fit(df_train, df_train["Frequency"], regressor__sample_weight=df_train["Exposure"]) .. GENERATED FROM PYTHON SOURCE LINES 150-152 دعنا نحسب أداء هذا خط الأساس للتنبؤ الثابت مع 3 مقاييس الانحدار المختلفة: .. GENERATED FROM PYTHON SOURCE LINES 152-193 .. code-block:: Python from sklearn.metrics import ( mean_absolute_error, mean_poisson_deviance, mean_squared_error, ) def score_estimator(estimator, df_test): """Score an estimator on the test set.""" y_pred = estimator.predict(df_test) print( "MSE: %.3f" % mean_squared_error( df_test["Frequency"], y_pred, sample_weight=df_test["Exposure"] )) print( "MAE: %.3f" % mean_absolute_error( df_test["Frequency"], y_pred, sample_weight=df_test["Exposure"] )) # تجاهل التوقعات غير الإيجابية، لأنها غير صالحة لـ # انحراف بواسون. mask = y_pred > 0 if (~mask).any(): n_masked, n_samples = (~mask).sum(), mask.shape[0] print( "تحذير: يُرجى إرجاع المُقدر تنبؤات غير صالحة، غير إيجابية " f" لـ {n_masked} عينات من {n_samples}. يتم تجاهل هذه التوقعات " "عند حساب انحراف بواسون.") print( "متوسط انحراف بواسون: %.3f" % mean_poisson_deviance( df_test["Frequency"][mask], y_pred[mask], sample_weight=df_test["Exposure"][mask], )) print("تقييم تردد متوسط ثابت:") score_estimator(dummy, df_test) .. rst-class:: sphx-glr-script-out .. code-block:: none تقييم تردد متوسط ثابت: MSE: 0.564 MAE: 0.189 متوسط انحراف بواسون: 0.625 .. GENERATED FROM PYTHON SOURCE LINES 194-201 نماذج (عامة) خطية --------------------------- نبدأ بنمذجة المتغير الهدف مع نموذج الانحدار الخطي الأقل تربيعًا (L2)، المعروف أكثر as الانحدار المحدب. نحن استخدام عقوبة منخفضة `alpha`، حيث نتوقع أن هذا النموذج الخطي ليتناسب مع هذه المجموعة الكبيرة من البيانات. .. GENERATED FROM PYTHON SOURCE LINES 201-211 .. code-block:: Python from sklearn.linear_model import Ridge ridge_glm = Pipeline( [ ("preprocessor", linear_model_preprocessor), ("regressor", Ridge(alpha=1e-6)), ] ).fit(df_train, df_train["Frequency"], regressor__sample_weight=df_train["Exposure"]) .. GENERATED FROM PYTHON SOURCE LINES 212-218 لا يمكن حساب انحراف بواسون على القيم غير الإيجابية التي تنبأ بها النموذج. بالنسبة للنماذج التي تعيد عددًا قليلاً من التوقعات غير الإيجابية (على سبيل المثال :class:`~sklearn.linear_model.Ridge`) نتجاهل العينات المقابلة، بمعنى أن انحراف بواسون المحسوب هو تقريبي. يمكن أن يكون النهج البديل لاستخدام :class:`~sklearn.compose.TransformedTargetRegressor` ميتا المقدر لتعيين ``y_pred`` إلى مجال إيجابي صارم. .. GENERATED FROM PYTHON SOURCE LINES 218-222 .. code-block:: Python print("تقييم Ridge:") score_estimator(ridge_glm, df_test) .. rst-class:: sphx-glr-script-out .. code-block:: none تقييم Ridge: MSE: 0.560 MAE: 0.186 تحذير: يُرجى إرجاع المُقدر تنبؤات غير صالحة، غير إيجابية لـ 595 عينات من 223745. يتم تجاهل هذه التوقعات عند حساب انحراف بواسون. متوسط انحراف بواسون: 0.597 .. GENERATED FROM PYTHON SOURCE LINES 223-232 بعد ذلك، نقوم بتركيب المُرجع بواسون على المتغير الهدف. نحن نحدد قوة التنظيم ``alpha`` إلى ما يقرب من 1e-6 على عدد العينات (أي `1e-12`) لمحاكاة المُرجع المحدب الذي يختلف L2 مصطلح العقوبة بشكل مختلف مع عدد العينات. نظرًا لأن المُرجع بواسون يقوم داخليًا بنمذجة سجل القيمة المستهدفة المتوقعة بدلاً من القيمة المتوقعة مباشرة (رابط تسجيل الدخول مقابل رابط الهوية)، العلاقة بين X و y لم تعد خطية تمامًا. لذلك يطلق على المُرجع بواسون نموذج خطي عام (GLM) بدلاً من نموذج خطي عادي كما هو الحال مع الانحدار المحدب. .. GENERATED FROM PYTHON SOURCE LINES 232-250 .. code-block:: Python from sklearn.linear_model import PoissonRegressor n_samples = df_train.shape[0] poisson_glm = Pipeline( [ ("preprocessor", linear_model_preprocessor), ("regressor", PoissonRegressor(alpha=1e-12, solver="newton-cholesky")), ] ) poisson_glm.fit( df_train, df_train["Frequency"], regressor__sample_weight=df_train["Exposure"] ) print("تقييم PoissonRegressor:") score_estimator(poisson_glm, df_test) .. rst-class:: sphx-glr-script-out .. code-block:: none تقييم PoissonRegressor: MSE: 0.560 MAE: 0.186 متوسط انحراف بواسون: 0.594 .. GENERATED FROM PYTHON SOURCE LINES 251-268 أشجار تعزيز التدرج للانحدار بواسون --------------------------------------------------------- أخيرًا، سنأخذ في الاعتبار نموذجًا غير خطي، وهو أشجار تعزيز التدرج. لا تتطلب النماذج الشجرية أن تكون البيانات الفئوية مشفرة بترميز أحادي الساخن: بدلاً من ذلك، يمكننا ترميز كل تسمية الفئة برقم عشوائي باستخدام :class:`~sklearn.preprocessing.OrdinalEncoder`. مع هذا الترميز، ستعامل الأشجار الميزات الفئوية كميزات مرتبة، والتي قد لا تكون سلوك مرغوب فيه دائمًا. ومع ذلك، فإن هذا التأثير محدود بالنسبة للأشجار العميقة بما يكفي لاستعادة الطبيعة الفئوية الميزات. الميزة الرئيسية لـ :class:`~sklearn.preprocessing.OrdinalEncoder` على :class:`~sklearn.preprocessing.OneHotEncoder` هو أنه سيجعل التدريب أسرع. يوفر تعزيز التدرج أيضًا إمكانية تركيب الأشجار بخسارة بواسون (مع رابط تسجيل الدخول الضمني) بدلاً من خسارة المربعات الأقل الافتراضية. هنا نحن فقط تركيب الأشجار بخسارة بواسون للحفاظ على هذا المثال موجز. .. GENERATED FROM PYTHON SOURCE LINES 268-299 .. code-block:: Python from sklearn.ensemble import HistGradientBoostingRegressor from sklearn.preprocessing import OrdinalEncoder tree_preprocessor = ColumnTransformer( [ ( "categorical", OrdinalEncoder(), ["VehBrand", "VehPower", "VehGas", "Region", "Area"], ), ("numeric", "passthrough", ["VehAge", "DrivAge", "BonusMalus", "Density"]), ], remainder="drop", ) poisson_gbrt = Pipeline( [ ("preprocessor", tree_preprocessor), ( "regressor", HistGradientBoostingRegressor(loss="poisson", max_leaf_nodes=128), ), ] ) poisson_gbrt.fit( df_train, df_train["Frequency"], regressor__sample_weight=df_train["Exposure"] ) print("تقييم أشجار تعزيز التدرج بواسون:") score_estimator(poisson_gbrt, df_test) .. rst-class:: sphx-glr-script-out .. code-block:: none تقييم أشجار تعزيز التدرج بواسون: MSE: 0.559 MAE: 0.184 متوسط انحراف بواسون: 0.575 .. GENERATED FROM PYTHON SOURCE LINES 300-311 مثل GLM بواسون أعلاه، يقلل نموذج الأشجار المعززة التدرج انحراف بواسون. ومع ذلك، بسبب قوة تنبؤية أعلى، يصل إلى قيم أقل من انحراف بواسون. تقييم النماذج بتقسيم تدريب / اختبار واحد عرضة للتقلبات العشوائية. إذا تسمح موارد الكمبيوتر، يجب التحقق من أن المقاييس المتقاطعة من شأنه أن يؤدي إلى استنتاجات مماثلة. يمكن أيضًا تصور الاختلاف النوعي بين هذه النماذج عن طريق مقارنة مخطط توزيع القيم المستهدفة الملاحظة بذلك من القيم المتوقعة: .. GENERATED FROM PYTHON SOURCE LINES 311-337 .. code-block:: Python fig, axes = plt.subplots(nrows=2, ncols=4, figsize=(16, 6), sharey=True) fig.subplots_adjust(bottom=0.2) n_bins = 20 for row_idx, label, df in zip(range(2), ["train", "test"], [df_train, df_test]): df["Frequency"].hist(bins=np.linspace(-1, 30, n_bins), ax=axes[row_idx, 0]) axes[row_idx, 0].set_title("Data") axes[row_idx, 0].set_yscale("log") axes[row_idx, 0].set_xlabel("y (التردد الملاحظ)") axes[row_idx, 0].set_ylim([1e1, 5e5]) axes[row_idx, 0].set_ylabel(label + " samples") for idx, model in enumerate([ridge_glm, poisson_glm, poisson_gbrt]): y_pred = model.predict(df) pd.Series(y_pred).hist( bins=np.linspace(-1, 4, n_bins), ax=axes[row_idx, idx + 1] ) axes[row_idx, idx + 1].set( title=model[-1].__class__.__name__, yscale="log", xlabel="y_pred (التردد المتوقع المتوقع)", ) plt.tight_layout() .. image-sg:: /auto_examples/linear_model/images/sphx_glr_plot_poisson_regression_non_normal_loss_002.png :alt: Data, Ridge, PoissonRegressor, HistGradientBoostingRegressor, Data, Ridge, PoissonRegressor, HistGradientBoostingRegressor :srcset: /auto_examples/linear_model/images/sphx_glr_plot_poisson_regression_non_normal_loss_002.png :class: sphx-glr-single-img .. GENERATED FROM PYTHON SOURCE LINES 338-358 تعرض البيانات التجريبية توزيع ذيل طويل لـ ``y``. في جميع النماذج، نتوقع التردد المتوقع لمتغير عشوائي، لذلك سنكون بالضرورة قيم متطرفة أقل من تلك الخاصة إدراكات هذا المتغير العشوائي. هذا يفسر أن وضع مخطط توزيع تنبؤات النموذج لا تتوافق بالضرورة مع القيمة الأصغر. بالإضافة إلى ذلك، فإن التوزيع الطبيعي المستخدم في ``Ridge`` له تباين ثابت، في حين أن توزيع بواسون المستخدم في ``PoissonRegressor`` و ``HistGradientBoostingRegressor``، التباين يتناسب مع القيمة المتوقعة المتوقعة. وبالتالي، من بين المقدرات التي تم النظر فيها، ``PoissonRegressor`` و ``HistGradientBoostingRegressor`` هي مسبقًا أفضل ملاءمة لنمذجة توزيع ذيل طويل للبيانات غير السلبية مقارنةً بنموذج ``Ridge`` الذي يفترض افتراضًا خاطئًا على توزيع المتغير الهدف. المقدر ``HistGradientBoostingRegressor`` لديه أكبر قدر من المرونة ويمكنه التنبؤ بقيم متوقعة أعلى. تجدر الإشارة إلى أننا كنا قد استخدمنا خسارة المربعات الأقل لـ نموذج ``HistGradientBoostingRegressor``. هذا من شأنه أن يفترض خطأً توزيع .. rst-class:: sphx-glr-timing **Total running time of the script:** (0 minutes 15.067 seconds) .. _sphx_glr_download_auto_examples_linear_model_plot_poisson_regression_non_normal_loss.py: .. only:: html .. container:: sphx-glr-footer sphx-glr-footer-example .. container:: binder-badge .. image:: images/binder_badge_logo.svg :target: https://mybinder.org/v2/gh/scikit-learn/scikit-learn/main?urlpath=lab/tree/notebooks/auto_examples/linear_model/plot_poisson_regression_non_normal_loss.ipynb :alt: Launch binder :width: 150 px .. container:: lite-badge .. image:: images/jupyterlite_badge_logo.svg :target: ../../lite/lab/index.html?path=auto_examples/linear_model/plot_poisson_regression_non_normal_loss.ipynb :alt: Launch JupyterLite :width: 150 px .. container:: sphx-glr-download sphx-glr-download-jupyter :download:`Download Jupyter notebook: plot_poisson_regression_non_normal_loss.ipynb ` .. container:: sphx-glr-download sphx-glr-download-python :download:`Download Python source code: plot_poisson_regression_non_normal_loss.py ` .. container:: sphx-glr-download sphx-glr-download-zip :download:`Download zipped: plot_poisson_regression_non_normal_loss.zip ` .. include:: plot_poisson_regression_non_normal_loss.recommendations .. only:: html .. rst-class:: sphx-glr-signature `Gallery generated by Sphinx-Gallery `_