Python數據分析學習筆記,今天分享下利用Python進行邏輯回歸,預測鐵達尼號乘客生存情況。
#導入2個Python常用數據分析的庫import numpy as npimport pandas as pd
#將數據源文件讀取#注意Windows環境下,需要用r轉義一下,不然讀取不進來train = pd.read_csv(r"C:\\Users\\Administrator\\Desktop\\train.csv")test = pd.read_csv(r"C:\\Users\\Administrator\\Desktop\\test.csv")print('訓練數據集:',train.shape,'測試數據集:',test.shape)
結果:表示訓練數據集為891行,12列;測試數據集為418行,11列,測試集少了一列Survived即我們後續需要通過邏輯回歸進行預測的。
#初步觀察數據情況#Pclass客艙等級#SibSp同代直系親屬數#Parch不同代直系親屬數#Cabin客艙號#Embarked登船港口#Fare船票價格full.head()
結果:用head函數可以默認查看前5行數據,便於我們初步掌握數據概況。
#描述性數據統計full.describe()
結果:用describe函數可以進行描述性數據統計,即我們常見的均值、標準差、中位數等。
#查看每一列數據類型和數據總數#Survived、Age、Fare、Cabin、Embarked有缺失full.info()
結果:用info函數可以查看各列的數據個數,便於我們快速定位那些列有缺失值。
#數據預處理,缺失值填充#數值型數據用均值或中位數填充,如Age#應用fillna函數,用於填充缺失值full['Age'] = full['Age'].fillna(full['Age'].mean())full['Fare'] = full['Fare'].fillna(full['Fare'].mean())
#分類型數據用最常見類別進行填充#先通過value_counts函數,查詢一下該列出現的各類型總數full['Embarked'].value_counts()
#看到量最多的是S,因此用它來填充確實項full['Embarked'] = full['Embarked'].fillna('S')
#因Cabin缺失較多,用新的『U』來表示(Unknow)full['Cabin'] = full['Cabin'].fillna('U')
#再次觀察一下數據,發現除Survived之外,都已經填充完成full.info()
#Sex為字符型欄位,需要轉換為數值型數據便於處理sex_mapDict = {'male':1,'female':0} #建立一個字典full['Sex'] = full['Sex'].map(sex_mapDict) #運用maple函數對Sex這一列進行重新編碼full.head()
#使用數據框的get-dummies( )對登船港口進行one-hot編碼embarkeddf = pd.DataFrame() #存放提取後的特徵embarkeddf = pd.get_dummies(full['Embarked'],prefix='Embarked') #使用get_dummies進行one-hot編碼,列名前綴是Embarkedembarkeddf.head(10)
結果:get_dummies函數的作用是將該列出現值的類型再重新劃分為子列,通過子列裡的布爾類型標識它的類型。
full = pd.concat([full,embarkeddf],axis=1) #添加one-hot編碼產生的虛擬變量(dummy variable)到full中full.head()
結果:通過concat函數將新增的列加到原數據表中。
full.drop('Embarked',axis=1,inplace=True) #將原Embarked列刪除full.head()
#對客艙等級Pclass進行同樣的one-hot編碼處理pclassdf = pd.DataFrame() #存放提取後的特徵pclassdf = pd.get_dummies(full['Pclass'],prefix='Pclass') #使用get_dummies進行one-hot編碼,列名前綴是Pclassfull = pd.concat([full,pclassdf],axis=1) #添加one-hot編碼產生的虛擬變量(dummy variable)到full中full.drop('Pclass',axis=1,inplace=True) #將原Pclass列刪除full.head()
#對姓名和頭銜做編碼處理#定義一個函數,從姓名中提取頭銜def gettitle(name): str1=name.split(',')[1] str2=str1.split('.')[0] str3=str2.strip() #strip用於移除字符串頭尾指定字符(默認為空格)return str3titleDf=pd.DataFrame() #存放提取後的特徵titleDf['title']=full['Name'].map(gettitle)titleDf.head()結果:
titleDf['title'].value_counts() #查詢頭銜的類別和數量結果:
#有些頭銜並不是常見頭銜,而且出現頻率比較低#這樣不利於機器學習,可將頭銜分為6類Officer,Royalty,Mrs,Miss,Mr,Master六種title_mapDict={ "Capt":"Officer", "Col":"Officer", "Major":"Officer", "Dr":"Officer", "Rev":"Officer", "Jonkheer":"Royalty", "Don":"Royalty", "Sir":"Royalty", "the Countess":"Royalty", "Dona":"Royalty", "Mme":"Mrs", "Mlle":"Miss", "Ms":"Mrs", "Mrs":"Mrs", "Mr":"Mr", "Miss":"Miss", "Master":"Master", "Lady":"Royalty"}titleDf['title']=titleDf['title'].map(title_mapDict)titleDf['title'].value_counts()結果:
titleDf = pd.get_dummies(titleDf['title']) titleDf.head()結果:
full = pd.concat([full,titleDf],axis=1) #添加one-hot編碼產生的虛擬變量(dummy variable)到full中full.head()結果:
#對船艙號Cabin進行同樣的one-hot編碼處理full['Cabin']=full['Cabin'].map(lambda c:c[0]) #取船艙號的首位做標識符cabindf = pd.DataFrame() #存放提取後的特徵cabindf = pd.get_dummies(full['Cabin'],prefix='Cabin') #使用get_dummies進行one-hot編碼,列名前綴是Cabinfull = pd.concat([full,cabindf],axis=1) #添加one-hot編碼產生的虛擬變量(dummy variable)到full中full.drop('Cabin',axis=1,inplace=True) #將原Cabin列刪除full.head()結果:
#家庭數據Parch、SibSp:對於家庭數據選擇計算家庭人數的方法提取特徵familydf=pd.DataFrame() #存放提取後的特徵familydf['family_size']=full['SibSp']+full['Parch']+1familydf['family_single']=familydf['family_size'].map(lambda a:1 if a==1 else 0)familydf['family_small']=familydf['family_size'].map(lambda a:1 if 2<=a<=4 else 0)familydf['family_large']=familydf['family_size'].map(lambda a:1 if 5<=a else 0)full = pd.concat([full,familydf],axis=1) #添加one-hot編碼產生的虛擬變量(dummy variable)到full中full.head()結果:
full.info()結果:
#查看相關性,使用corr生成相關係數矩陣corrDf = full.corr()corrDf結果:
#查看各個特徵與生存情況的相關性corrDf['Survived'].sort_values(ascending=False)結果:
#特徵選擇full_x=pd.concat([titleDf,pclassdf,familydf,full['Fare'],cabindf,embarkeddf,full['Sex']],axis=1)full_x.head()結果:
print(full_x.shape)結果:
#構建模型#原始數據集有891條數據sourceRow=891#原始數據集特徵source_x=full_x.loc[0:sourceRow-1,:]#原始數據集標籤source_y=full.loc[0:sourceRow-1,'Survived']#預測數據集特徵pre_x=full_x.loc[sourceRow:,:] #取sourceRow之後的數據source_x.head()結果:
#建立訓練數據和測試數據from sklearn.model_selection import train_test_splittrain_x,test_x,train_y,test_y=train_test_split(source_x,source_y,train_size=0.8)#數據集大小print('原始數據集特徵',source_x.shape, '訓練數據集特徵',train_x.shape, '測試數據集特徵',test_x.shape)print('原始數據集標籤',source_y.shape, '訓練數據集標籤',train_y.shape, '測試數據集標籤',test_y.shape)結果:
#導入機器算法from sklearn.linear_model import LogisticRegressionmodel=LogisticRegression() #創建邏輯回歸模型model.fit(train_x,train_y) #訓練模型#評估模型,查看正確率model.score(test_x,test_y)結果:可以看到這個正確率還是非常高的,可以用來後續的預測。
#通過機器學習模型,對預測數據生存情況進行預測pre_y=model.predict(pre_x)#將預測結果轉換為整數型pre_y=pre_y.astype(int)#乘客IDpassenger_ID=full.loc[sourceRow:,'PassengerId']#乘客名字passenger_Name=full.loc[sourceRow:,'Name']#數據框:乘客ID,預測結果preDf=pd.DataFrame({'PassengerId':passenger_ID,'Name':passenger_Name,'Survived':pre_y})preDf.head()結果:預測結果為乘客編號、乘客姓名與是否生存。
#將文件保存到本地preDf.to_csv('tintanic_prd.csv',index=False)