Titanic作为Kaggle官方网站的第一篇入门比赛,如果你想学习kaggle,那么从它开始无疑是比较好的一个选择。
首先贴一下网址:https://www.kaggle.com/c/titanic
先描述一下问题:泰坦尼克号的沉没是历史上最臭名昭著的沉船事件之一。1912年4月15日,泰坦尼克号在处女航中撞上冰山沉没,2224名乘客和船员中1502人遇难。这一耸人听闻的悲剧震惊了国际社会,并导致了更好的船舶安全条例。沉船造成如此巨大人员伤亡的原因之一是没有足够的救生艇来容纳乘客和船员。虽然在沉船事件中幸存下来也有一些运气的因素,但有些人比其他人更有可能幸存下来,比如妇女、儿童和上层阶级。在这个挑战中,我们要求你完成对可能存活下来的人的分析。我们特别要求你们运用机器学习工具来预测哪些乘客在灾难中幸存下来。
数据集共3个文件,train.csv是我们的训练文件,是一个12维的数据,其中11维是特征,分别是乘客id,pclass, name, sex, age, sibSP, paoch, Ticket, Fare, Cabin, Embarked; 第二行“survived”是我们的标签,表示是否存活,0表示未存活,1表示为存活。
实际上这是一个二分类的问题,关键在于如何选择特征。这里有几个问题:
1)需要将类别属性,如性别‘sex‘中的male或female转成数值型属性。这里有两种解决办法
第一种是采用替换法,直接将male替换成0,female替换成female
path=r"E:\研究生\courses\kaggle\titanic\train.csv"
# 训练数据
f=open(path,encoding='UTF-8')
train_df=pd.read_csv(f)
sex_mapping={'male':1 ,'female':0}
train_df['Sex']=train_df['Sex'].map(sex_mapping)
第二种是通过one-hot编码,生成一个二维向量,添加到原始数据中
dummies_cabin=pd.get_dummies(train_df['Sex'],prefix='Sex')
train_df=pd.concat([train_df,dummies_cabin],axis=1)
train_df.drop(['Cabin'],axis=1,inplace=True)
2)根据相关性进行特征选择,我们使用皮尔森相关性进行特征选择:
corrDf = data_train.corr()
print(corrDf['Survived'].sort_values(ascending =False))
选择相关性较大的特征
3)缺失数据,对于缺失数据我们一般采用删除或填充的方法,对于数值型属性我们可以填充中位数,而对于字符型数据我们可以填充众数,这里由于年龄age属性很难填充而且填充容易对最后实验结果造成干扰,所以我们决定不使用年龄特征
最终我们决定使用pclass, sex, SibSp, Parch四个属性作为最终的特征。
x_train=train_df.iloc[:,[4,6,7]]
y_train=train_df.iloc[:,1]
对测试文件进行同样的操作,我们就可以调用机器学习模型来进行分类了。
分类器的选择很多,这里我选择随机森林分类器来进行分类,此外还可以选择SVM,KNN,朴素贝叶斯,也可以选择kaggle神器XGBoost进行分类,只是Xgboost适合于数据量比较大的训练集,我们只有891条数据,所以这里没有使用XGBoost分类。
model=RandomForestClassifier(n_estimators=500)
model.fit(x_train,y_train)
y_pred=model.predict(x_test)
最终将结果按照要求保存到csv文件。
result=pd.DataFrame({'PassengerId':test_df['PassengerId'],'Survived':y_pred.astype(np.int32)})
result.to_csv(r"submission.csv",index=False)
提交过程中,你可能需要不断调参,选择不同的模型来达到一个更高的准确性,你可以选择网格搜索GridSearchCV或者蚁群算法来寻找最优解~
当然,这只是kaggle入门的一个比较简单的例子,你可以选择通过kernel来了解大家都是如何做的,这也是kaggle可以让你不断学习的地方。
最后贴一下整个代码:
import pandas as pd
import numpy as np
from sklearn.ensemble import RandomForestClassifier,VotingClassifier
from sklearn.metrics import accuracy_score
path=r"E:\研究生\courses\kaggle\titanic\train.csv"
path2=r"E:\研究生\courses\kaggle\titanic\test.csv"
path3=r"E:\研究生\courses\kaggle\titanic\gender_submission.csv"
# 训练数据
f=open(path,encoding='UTF-8')
train_df=pd.read_csv(f)
corrDf=train_df.corr()
print(corrDf)
sex_mapping={'male':1 ,'female':0}
train_df['Sex']=train_df['Sex'].map(sex_mapping)
# 将训练集数据的Sex one-hot编码
# dummies_cabin=pd.get_dummies(train_df['Sex'],prefix='Sex')
# train_df=pd.concat([train_df,dummies_cabin],axis=1)
# df.drop(['Cabin'],axis=1,inplace=True)
print(train_df.head(10))
x_train=train_df.iloc[:,[4,6,7]]
y_train=train_df.iloc[:,1]
# 测试数据
f=open(path2,encoding="UTF-8")
test_df=pd.read_csv(f)
# 将测试集数据的Sex one-hot编码
# dummies_cabin=pd.get_dummies(test_df['Sex'],prefix='Sex')
# test_df=pd.concat([test_df,dummies_cabin],axis=1)
f=open(path3,encoding="UTF-8")
df=pd.read_csv(f)
y_test=df.iloc[:,1]
test_df['Sex']=test_df['Sex'].map(sex_mapping)
x_test=test_df.iloc[:,[3,5,6]]
model=RandomForestClassifier(n_estimators=500)
model.fit(x_train,y_train)
y_pred=model.predict(x_test)
score=accuracy_score(y_pred,y_test)
print('预测准确率为:',score)
result=pd.DataFrame({'PassengerId':test_df['PassengerId'],'Survived':y_pred.astype(np.int32)})
result.to_csv(r"E:\研究生\courses\kaggle\titanic\submission.csv",index=False)