**بسم الله الرحمن الرحیم** # مقدمه سیستم اشتراک گذاری دوچرخه یا سیستم دوچرخه عمومی ، یک سرویس است که در آن دوچرخه در مدت زمان کوتاهی برای استفاده مشترک افراد در نظر گرفته می شود . در این سیستم ، مردم می توانند دوچرخه را از ایستگاه های مختلف مانند ایستگاه A امانت بگیرند و در ایستگاه دیگری مانند B تحویل دهند . با استفاده از این سیستم ، افراد زیادی می توانند از دوچرخه استفاده کنند . هدف اصلی سیستم اشتراک گذاری دوچرخه ، دسترسی رایگان و مقرون به صرفه به دوچرخه برای سفر های کوتاه در یک منطقه شهری و به عنوان جایگزینی برای وسایل حمل و نقل موتوری است که منجر به کاهش تراکم ترافیک ، سر و صدا و آلودگی هوا می شود. میزان استفاده مردم از دوچرخه به عوامل متعددی مانند فصل ، دما ، وضعیت آب و هوا و ... بستگی دارد . در این پروژه قصد داریم مجموعه داده هایی را که مربوط به سیستم اشتراک گذاری دوچرخه می باشد ، بررسی نماییم و با استفاده از آن ها پیش بینی کنیم که با توجه به عواملی که داده شده است ، چند بار ممکن است که دوچرخه امانت گرفته شود . # مجموعه داده[^Dataset] مجموعه داده این سیستم ، توسط آقای هادی فنایی ترک تهیه شده است و از kaggle گرفته شده است . این مجموعه داده شامل 17381 داده است که اطلاعات مربوط به تعداد اجاره دوچرخه در 19 روز اول ماه داده شده است و با بررسی این اطلاعات باید تعداد اجاره دوچرخه از روز 20 ام تا پایان ماه را پیش بینی کنیم .این داده ها شامل 12 متغیربه شرح زیر می باشد: |datetime|season|holiday|workingday|weather|temp|atemp|humidity|windspeed|casual|registered|count| - تاریخ و زمان اجاره دوچرخه [^Date time] - فصلی [^Season] که دوچرخه در آن اجاره داده شده است را با یک اعدد صحیح در بازه [1,4] نشان می دهد . بدین صورت که عدد 1 نماد فصل بهار ، عدد 2 نماد فصل تابستان ، عدد 3 نماد فصل پاییز و عدد 4 نماد فصل زمستان است . - تعطیل [^Holiday] بودن یا نبودن روز اجاره دوچرخه را نشان می دهد . اگر روز تعطیل باشد ، عدد 1 و در غیر این صورت عد 0 را نشان می دهد. - نشان دهنده کاری [^Workingday] یا غیر کاری بودن روز اجاره دوچرخه است . اگر جزو روز های کاری باشد ، عدد 1 و در غیر این صورت عدد 0 را نشان می دهد . - وضعیت آب و هوا [^Weather] را با یک عدد صحیح در بازه [1,4] نشان می دهد . بدین صورت که عدد 1 نماد آب و هوای آفتابی ، عدد 2 نماد آب و هوای غبار آلود ، عدد 3 نماد آب و هوای برفی و عدد 4 نماد بارندگی سنگین است. - دما [^Temp] بر حسب درجه سلسیوس - دمای ظاهری [^Atemp] برحسب درجه سلسیوس - درصد رطوبت نسبی [^Humidity] - سرعت باد [^Windspeed] - تعداد افرادی که بدون ثبت نام [^Casual] ، دوچرخه اجاره کرده اند - تعداد افرادی که برای اجاره دوچرخه ثبت نام [^Registered] کرده اند - تعداد [^Count]کل کسانی که دوچرخه اجاره کرده اند این 12 ویژگی برای داده ها ذکر شده است و ما باید با بررسی این داده ها بتوانیم پیش بینی کنیم که برای داده های با ویژگی ها جدید میزان استفاده از دوچرخه چقدر می باشد . در این قسمت دو راه وجود دارد : راه اول: پردازش اطلاعات را برای داده هایی که اجاره کننده ، ثبت نام کرده باشد و یا نکرده باشد را جدا انجام دهیم و نتایج را نیز جدا بدست آوریم . راه دوم : می توانیم به طور کلی تعداد اجاره دوچرخه را حساب کنیم و میان کسی که ثبت نام کرده است و کسی که ثبت نام نکرده است ، تفاوتی قائل نشویم . + [اطلاعات کامل مجموعه داده](https://www.kaggle.com/c/bike-sharing-demand/data) # کارهای مرتبط این مساله از نوع یادگیری با ناظر است . این روش ، یک روش عمومی در یادگیری ماشین است که در آن به یک سیستم، مجموعه ای از جفتهای ورودی – خروجی ارائه شده و سیستم تلاش میکند تا تابعی از ورودی به خروجی را فرا گیرد. یادگیری تحت نظارت نیازمند تعدادی داده ورودی به منظور آموزش سیستم است که به دو دسته تقسیم می شود: **تقسیم بندی**[^Classification] : در این روش مقادیر ممکن خروجی را به صورت چند کلاس در نظر می گیریم . برای مثال بازه های 0 تا 20 ،20 تا 40 و ... . با توجه به کلاس ها، مقدار خروجی در هر کلاس قرار گرفت ، داده به آن کلاس تعلق می گیرد . **رگرسیون** [^Regression] :تحلیل رگرسیونی فن و تکنیکی آماری برای بررسی و مدل سازی ارتباط بین متغیر وابسته و متغیر مستقل بوده و هدف آن پیشبینی متغیر وابسته از روی متغیر و یا متغیرهای مستقل میباشد . + [تقسیم بندی و رگرسیون](http://scikit-learn.org/stable/tutorial/statistical_inference/supervised_learning.html) با توجه به توضیحات بالا ، اگر بخواهیم مشاهدات را در یک بسته محدود از برچسب ها دسته بندی کنیم یا به عبارت دیگر داده ها یا اشیا مشاهده شده را نام گذاری کنیم ، از روش تقسیم بندی استفاده می کنیم . اما اگر هدف این باشد که یک متغیر هدف پیوسته [^continuous target variable] را پیش بینی کنیم ، از روش رگرسیون استفاده می کنیم . الگوریتم هایی که برای حل این مسئله استفاده می شوند از نوع رگرسیون هستند که در ادامه توضیح داده می شود: **رگرسیون خطی** [^Linear regression] : در این روش، خطی را مشخص می کنیم به طوری که مجموع فاصله نقاط تا آن خط مینیمم باشد . در این مسئله ، محور عمودی نمودار تعداد کرایه دوچرخه و محور افقی شماره دوچرخه می باشد و نقاط نمودار تعداد کرایه هر دوچرخه را نشان می دهد. خط مورد نظر به صورت زیر است: ![](https://boute.s3.amazonaws.com/211-Slide1.JPG) در این جا بردار [X=[x1,x2,…,xn و [W=[w1,w2,…,wn را داریم . خط مورد نظر ما از رابطه زیر بدست می آید که در آن y مقادیر واقعی(یعنی تعداد دوچرخه ها) و XW خط است . حاصل این فرمول ، خطی است که مینیمم فاصله را تا تمام نقاط در رگرسیون دارد . ![](https://boute.s3.amazonaws.com/211-32028e85feb455d07503a027ba607eafc7909976.png) قطعه کد زیر مثالی از متدی در زبان برنامه نویسی پایتون را نشان می دهد که رگرسیون خطی را با بررسی ورودی ها محاسبه می کند : ...from sklearn import linear_model ...clf = linear_model.LinearRegression() ...clf.fit ([[0, 0], [1, 1], [2, 2]], [0, 1, 2]) ...clf.coef_ **رگرسیون خطی-راسی** [^Ridge Linear Regression ] : در این روش همانند رگرسیون خطی به دنبال خطی هستیم که نقاط را به دو قسمت تقسیم کند و از نقاط مرزی کمترین فاصله را داشته باشد. با این تفاوت که علاوه بر پیدا کردن کمترین فاصله می خواهیم ضرایب خط یعنی W نیز کمترین مقدار را داشته باشد.بنابراین از فرمول زیر استفاده می کنیم: ![](https://boute.s3.amazonaws.com/211-11f0787a645f4b5f2b810c0d00618785b58ff574.png) مقدار پارامتر a با توجه به این که بخواهیم قسمت اول عبارت کمینه شود یا قسمت دوم ، تنظیم می شود. هر چقدر مقدار a بیشتر باشد ، مقدار قسمت اول عبارت کمینه تر می شود و هر چقدر کتر باشد مقدار قسمت دوم عبارت کمینه تر می شود. ![ رگرسیون خطی-راسی ](https://boute.s3.amazonaws.com/211-plot_ridge_path_001.png) قطعه کد زیر مثالی از متدی در زبان برنامه نویسی پایتون را نشان می دهد که با بررسی داده های ورودی ، رگرسیون خطی راسی را پیدا می کند.` ...from sklearn import linear_model ...clf = linear_model.Ridge (alpha = .5) ...clf.fit ([[0, 0], [0, 0], [1, 1]], [0, .1, 1]) ...clf.coef ...clf.intercept_ + [رگرسیون خطی و خطی-راسی](http://scikit-learn.org/stable/modules/linear_model.html) **ماشین بردار پشتیبانی **[^Support vector machines] : یکی از روشهای یادگیری بانظارت است که از آن برای طبقهبندی و رگرسیون استفاده میکنند . در این روش نقاط خروجی یعنی تعداد دوچرخه ها را در یک صفحه مختصات داریم و به دنبال خطی هستیم که نقاط خروجی را به دو دسته طوری تقسیم کند که فاصله نقاط مرزی تا خط حد اکثر باشد. روش حل : ما مجوعه داده های D آزمایش شامل n عضو(نقطه)را در اختیار داریم که به صورت زیر تعریف می شود: ![](https://boute.s3.amazonaws.com/211-eee90c97797d0706f1ac0de4d1f44807.png) هدف پیدا کردن ابرصفحه جداکننده با بیشترین فاصله از نقاط حاشیه ای است که نقاط با yi=1 را از نقاط باyi=-1 جدا کند. هر ابر صفحه می تواند به صورت مجموعه ای از نقاط که شرط زیر را ارضا می کند نوشت: ![](https://boute.s3.amazonaws.com/211-6fbb2f26a8cfa99c5f3f84e292b25873.png) بردار W بردار نرمال است، که به ابرصفحه عمود است. ما می خواهیم و w,b را طوری انتخاب کنیم که بیشترین فاصله بین ابر صفحه های موازی که داده ها را از هم جدامی کنند، ایجاد شود. این ابرصفحه ها با استفاده از رابطه زیر توصیف می شوند. ![](https://boute.s3.amazonaws.com/211-15d93fd450bc218795d5a852ebf9e137.png) و ![](https://boute.s3.amazonaws.com/211-647d66a37fe5803ffd52510297676436.png) شکل زیر این روش را نشان می دهد : ![ماشین بردار پشتیبانی](https://boute.s3.amazonaws.com/211-Svm_max_sep_hyperplane_with_margin.png) در زبان پایتون ، متدی برای ماشین بردار پشتیبان وجود دارد که قطعه کد زیر مثالی از آن است``: ...from sklearn import svm ...X = [[0, 0], [2, 2]] ...y = [0.5, 2.5] ...clf = svm.SVR() ...clf.fit(X, y) + [ماشین بردار پشتیبان](http://scikit-learn.org/stable/modules/svm.html)# آزمایشها # کارهای آینده # مراجع [1] Fanaee-T, Hadi, and Gama, Joao, Event labeling combining ensemble detectors and background knowledge, Progress in Artificial Intelligence (2013): pp. 1-15, Springer Berlin Heidelberg. [2] Jimmy Du,Forecasting Bike Rental Demand , Rolland He, Zhivko Zhechev [3] Yu-Chun Yin, Chi-Shuen Lee, and Yu-Po ,Demand Prediction of Bicycle Sharing Systems, Wong Stanford University [4] Ford Rylander , Bo Peng and Jeff Wheeler , Bike Share Usage Prediction in London **پیوندهای مفید** + [صفحه مربوط به مسابقه](https://www.kaggle.com/c/bike-sharing-demand)**جنگل تصادفی**[^Random Forest] : این الگوریتم از تعداد زیادی درخت تصمیم درست میشود که حالت خروجی بهدست آمده از این درخت، منحصربهفرد است . از این الگوریتم هم برای دادههای تقسیم بندی و هم دادههای رگرسیون میتوان استفاده کرد که با توجه به توضیحات قبلی برای این مسئله ، از نوع رگرسیون استفاده می کنیم . در این الگوریتم ، تعداد زیادی درخت تصمیم[^Decision Tree] با داده ها رسم می کنیم و حاصل عبارت زیر را برای هر درخت محاسبه می کنیم . ![فرمول محاسبه برای انتخاب درخت تصمیم بهینه](http://uploadgoogle.ir/uploads/1451024722521.jpg) در این فرمول ، Y مقدار واقعی و y مقداری است که با استفاده از درخت تصمیم بدست می آید . درختی که حاصل آن کمترین مقدار را داشته باشد به عنوان درخت تصمیم مسئله انتخاب می کنیم. برای رسم درخت تصمیم ، ابتدا از بین ویژگیهای دادههای مسئله ، یک ویژگی را به عنوان شروع درخت تصمیم درنظر میگیریم . سپس با استفاده از ویژگیهای دیگر داده ها، درخت تصمیم را تا رسیدن به برگ ها که جواب های مسئله هستند، ادامه می دهیم . بعد از مشخص شدن درخت تصمیم مسئله ، پاسخ داده های test را با استفاده از این درخت تصمیم بدست میآوریم . ![درخت تصمیم](http://uploadgoogle.ir/uploads/1451024844271.png) مهم ترین مزیت های استفاده از الگوریتم Random Forest : 1. یکی از دقیق ترین الگوریتمهای یادگیری دردسترس است که برای بسیاری از مجموعه دادهها یک طبقه بندی بسیار دقیق ارائه میدهد. 2. برای مجموعه دادههای بسیار بزرگ بهخوبی کار میکند . 3. تقریب خوبی در مورد این که کدام متغیر برای طبقه بندی مناسب است ارائه میدهد. 4. این الگوریتم در مقایسه با الگوریتم رگرسیون خطی ، جواب های دقیق تری را می دهد . برای مثال ، تابع (log(x را با هر دو روش پیش بینی می کنیم . ![مقایسه الگوریتم جنگل تصادفی با رگرسیون خطی](http://uploadgoogle.ir/uploads/1451024962311.png) همان طور که از نمودار ها مشخص است ، این الگوریتم کارایی بیشتری دارد و پاسخ خای دقیق تری را ارائه می دهد . در زبان پایتون ، متدی برای محاسبه این الگوریتم وجود دارد که قطعه کد زیر آن را نشان می دهد : ...from sklearn.ensemble import RandomForestClassifier ...forest = RandomForestClassifier(n_estimators = 100) ...forest = forest.fit(train_data[0::,1::],train_data[0::,0]) ...output = forest.predict(test_data) + [آشنایی با Random Forest](http://blog.yhathq.com/posts/random-forests-in-python.html) + [بررسی الگوریتم Random Forest](https://www.quora.com/How-does-random-forest-work-for-regression-1l) + [مثالی از Random Forest ](http://www.slideshare.net/m80m07/random-forest) + [آشنایی با درخت تصمیم](http://scikit-learn.org/stable/modules/tree.html) **افزایش شیب**[^Gradient Boosting] : یکی از الگوریتم های قدرتمند در زمینه ماشین های یادگیرنده است که در زمینه های رگرسیون ، تقسیم بندی و رتبه بندی کاربرد دارد . فرض کنید داده هایی به صورت (x1,y1),(x2,y2),… داریم و تابع (F(x با حداقل هزینه را داریم . اگر داشته باشیم : ![](http://uploadgoogle.ir/uploads/1451025325241.png) بدست آوردت تابع h باعث بهبود الگوریتم میشود . در واقع اگر مقداری که تابع F می دهد با h جمع شود مقدار واقعی حاصل می شود. طبق رابطه بالا داریم : ![](http://uploadgoogle.ir/uploads/1451025341391.png) تابع هزینه را به صورت زیر تعریف میکنیم : ![تابع هزینه](http://uploadgoogle.ir/uploads/1451027378291.png) می خواهیم مقدار عبارت زیر را با استفاده از تنظیم (F(xi ها مینیمم کنیم : ![](http://uploadgoogle.ir/uploads/1451026890041.png) سپس تابع شیب منفی را که قرینه تابع h مورد نظر ما است به صورت زیر تعریف میکنیم : ![تابع شیب منفی](http://uploadgoogle.ir/uploads/145102693581.png) و داریم : ![](http://uploadgoogle.ir/uploads/145102699431.png) تابع هزینه ، شیب منفی و h به صورت زیر حاصل می شود : ![](http://uploadgoogle.ir/uploads/1451027102111.png) ![](http://uploadgoogle.ir/uploads/1451027153011.png) ارجاع به مقاله شماره 6 # آزمایشها از بین الگوریتم هایی که برای حل این مسئله ارائه شد ، دو مورد random Forest و Gradient Boosting با توجه به مزیت هایشان نسبت به الگوریتم های دیگر برای ارزیابی مسئله انتخاب شده اند . پیاده سازی این الگوریتم ها با استفاده از کتابخانه sklearn زبان پایتون انجام شده است . در این قسمت پس از پیاده سازی الگوریتم های فوق ، داده های train را جهت یادگیری ماشین می دهیم، سپس ماشین با استفاده از دانشی که بدست آورده ، تعداد اجاره دوچرخه برای زمان هایی که در داده های test داده شده است را پیش بینی می کند . کد های پیاده سازی این الگوریتم در لینک زیر قرار دارد : + [کد های پیاده سازی پیش بینی میزان استفاده از دوچرخه ](https://github.com/hajihosseini/bike-sharing-demand) مجموعه داده های مسئله را از [اینجا ](https://www.kaggle.com/c/bike-sharing-demand/data) دانلود کنید و در کنار کدها قرار دهید . فایل RandomForest.py الگوریتم Random Forest را پیاده سازی می کند و پاسخ داده های test یعنی پیش بینی میزان استفاده از دوچرخه برای 10 روز آخر ماه را محاسبه می کند و نتیجه را در فایل RandomForest.csv ذخیره می کند . فایل GradientBoosting.py نیز الگوریتم Gradient Boosting را پیاده سازی می کند و مانند الگوریتم قبلی ، پاسخ داده های test را در Gradient Boosting.csv ذخیره می کند. بعد از به دست آوردن جواب های مسئله با استفاده از الگوریتم های فوق ، باید پاسخ ها را ارزیابی کنیم تا میزان خطای هر الگوریتم مشخص شود . با توجه به این که در مجموعه داده ها ، پاسخ داده های test را نداریم ، نمی توانیم مستقیما میزان خطا را محاسبه کنیم . به همین علت میزان خطا را با استفاده از داده های مجموعه train محاسبه می کنیم . در فایل RF_evaluate.py فایل RandomForest.csv که حاصل اجرای الگوریتم RandomForest برای این مسئله است را به عنوان ورودی می دهیم و میزان استفاده از دوچرخه را برای مجموعه داده های train محاسبه می کنیم . سپس این مقدار را با مقدار اصلی مقایسه می کنیم . همین کار را در مورد الگوریتم Gradient Boosting نیز با فایل GB_evaluate.py انجام می دهیم . میزان خطا را با فرمول زیر محاسبه می کنیم : ![محاسبه میزان خطا](http://uploadgoogle.ir/uploads/1451037890961.jpg) نتیجه میزان خطا برای دو الگوریتم فوق به صورت زیر است : ![مقایسه میزان خطای الگوریتم ها](http://uploadgoogle.ir/uploads/1451038951591.jpg) همان طور که از نتایج جدول مشخص است ، الگوریتم Random Forest میزان خطای کمتری نسبت به الگوریتم Gradient Boosting دارد و برای این مسئله مناسب تر است . # کارهای آینده # مراجع [1] Fanaee-T, Hadi, and Gama, Joao, Event labeling combining ensemble detectors and background knowledge, Progress in Artificial Intelligence (2013): pp. 1-15, Springer Berlin Heidelberg. [2] Jimmy Du,Forecasting Bike Rental Demand , Rolland He, Zhivko Zhechev [3] Yu-Chun Yin, Chi-Shuen Lee, and Yu-Po ,Demand Prediction of Bicycle Sharing Systems, Wong Stanford University [4] Ford Rylander , Bo Peng and Jeff Wheeler , Bike Share Usage Prediction in London [5] Andy Liaw and Matthew,Classification and Regression by randomForest [6] Cheng Li ,A Gentle Introduction to Gradient Boosting [7] Arnab Kumar Datta , Predicting bike-share usage patterns with machine learning [8] Hanzhong Xu and Meng Meng , Bike Sharing Demand **پیوندهای مفید** + [صفحه مربوط به مسابقه](https://www.kaggle.com/c/bike-sharing-demand) + [سیستم اجاره دوچرخه در زبان R](http://www.analyticsvidhya.com/blog/2015/06/solution-kaggle-competition-bike-sharing-demand/) + [سیستم اجاره دوچرخه در زبان پایتون](http://efavdb.com/bike-share-forecasting/)