贪心科技机器学习训练营(六)

举报
毛利 发表于 2021/07/15 06:10:38 2021/07/15
【摘要】 先把来源写上 来源:贪心学院,https://www.zhihu.com/people/tan-xin-xue-yuan/activities 对于这个Titanic泰坦尼克号生存绝对有笔记 Seaborn数据可视化 通过Logistic Regression预测Titanic乘客是否能在事故中生还 导入工具库和数据查看缺失数据 2.1. 年龄2.2. 仓位2...

先把来源写上

来源:贪心学院,https://www.zhihu.com/people/tan-xin-xue-yuan/activities

对于这个Titanic泰坦尼克号生存绝对有笔记

Seaborn数据可视化

通过Logistic Regression预测Titanic乘客是否能在事故中生还

  1. 导入工具库和数据
  2. 查看缺失数据
  3. 数据分析
  4. Logistic Regression

1. 导入工具库和数据

import numpy as np 
import pandas as pd 

from sklearn import preprocessing
import matplotlib.pyplot as plt 
plt.rc("font", size=14)
import seaborn as sns
sns.set(style="white") #设置seaborn画图的背景为白色
sns.set(style="whitegrid", color_codes=True)

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
# 将数据读入 DataFrame
df = pd.read_csv("./titanic_data.csv")

# 预览数据
df.head()

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
pclass survived name sex age sibsp parch ticket fare cabin embarked
0 1.0 1.0 Allen, Miss. Elisabeth Walton female 29.0000 0.0 0.0 24160 211.3375 B5 S
1 1.0 1.0 Allison, Master. Hudson Trevor male 0.9167 1.0 2.0 113781 151.5500 C22 C26 S
2 1.0 0.0 Allison, Miss. Helen Loraine female 2.0000 1.0 2.0 113781 151.5500 C22 C26 S
3 1.0 0.0 Allison, Mr. Hudson Joshua Creighton male 30.0000 1.0 2.0 113781 151.5500 C22 C26 S
4 1.0 0.0 Allison, Mrs. Hudson J C (Bessie Waldo Daniels) female 25.0000 1.0 2.0 113781 151.5500 C22 C26 S
print('数据集包含的数据个数 {}.'.format(df.shape[0]))

  
 
  • 1
数据集包含的数据个数 1310.

  
 
  • 1

2. 查看缺失数据

# 查看数据集中各个特征缺失的情况
df.isnull().sum()

  
 
  • 1
  • 2
pclass 1
survived 1
name 1
sex 1
age 264
sibsp 1
parch 1
ticket 1
fare 2
cabin 1015
embarked 3
dtype: int64

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12

2.1. 年龄

# "age" 缺失的百分比 
print('"age" 缺失的百分比  %.2f%%' %((df['age'].isnull().sum()/df.shape[0])*100))

  
 
  • 1
  • 2
"age" 缺失的百分比  20.15%

  
 
  • 1

约 20% 的乘客的年龄缺失了. 看一看年龄的分别情况.

ax = df["age"].hist(bins=15, color='teal', alpha=0.6)
ax.set(xlabel='age')
plt.xlim(-10,85)
plt.show()

  
 
  • 1
  • 2
  • 3
  • 4

在这里插入图片描述
由于“年龄”的偏度不为0, 使用均值替代缺失值不是最佳选择, 这里可以选择使用中间值替代缺失值

注: 在概率论和统计学中,偏度衡量实数随机变量概率分布的不对称性。偏度的值可以为正,可以为负或者甚至是无法定义。在数量上,偏度为负(负偏态)就意味着在概率密度函数左侧的尾部比右侧的长,绝大多数的值(不一定包括中位数在内)位于平均值的右侧。偏度为正(正偏态)就意味着在概率密度函数右侧的尾部比左侧的长,绝大多数的值(不一定包括中位数)位于平均值的左侧。偏度为零就表示数值相对均匀地分布在平均值的两侧,但不一定意味着其为对称分布。

# 年龄的均值
print('The mean of "Age" is %.2f' %(df["age"].mean(skipna=True)))
# 年龄的中间值
print('The median of "Age" is %.2f' %(df["age"].median(skipna=True)))

  
 
  • 1
  • 2
  • 3
  • 4
The mean of "Age" is 29.88
The median of "Age" is 28.00

  
 
  • 1
  • 2

2.2. 仓位

# 仓位缺失的百分比
print('"Cabin" 缺失的百分比 %.2f%%' %((df['cabin'].isnull().sum()/df.shape[0])*100))

  
 
  • 1
  • 2
"Cabin" 缺失的百分比 77.48%

  
 
  • 1

约 77% 的乘客的仓位都是缺失的, 最佳的选择是不使用这个特征的值.

2.3. 登船地点

# 登船地点的缺失率
print('"Embarked" 缺失的百分比 %.2f%%' %((df['embarked'].isnull().sum()/df.shape[0])*100))

  
 
  • 1
  • 2
"Embarked" 缺失的百分比 0.23%

  
 
  • 1

只有 0.23% 的乘客的登船地点数据缺失, 可以使用众数替代缺失的值.

print('按照登船地点分组 (C = Cherbourg, Q = Queenstown, S = Southampton):')
print(df['embarked'].value_counts())
sns.countplot(x='embarked', data=df, palette='Set2')
plt.show()

  
 
  • 1
  • 2
  • 3
  • 4
按照登船地点分组 (C = Cherbourg, Q = Queenstown, S = Southampton):
S 914
C 270
Q 123
Name: embarked, dtype: int64

  
 
  • 1
  • 2
  • 3
  • 4
  • 5

在这里插入图片描述

print('乘客登船地点的众数为 %s.' %df['embarked'].value_counts().idxmax())

  
 
  • 1
乘客登船地点的众数为 S.

  
 
  • 1

由于大多数人是在南安普顿(Southhampton)登船, 可以使用“S”替代缺失的数据值

2.4. 根据缺失数据情况调整数据

基于以上分析, 我们进行如下调整:

  • 如果一条数据的 “Age” 缺失, 使用年龄的中位数 28 替代.
  • 如果一条数据的 “Embarked” 缺失, 使用登船地点的众数 “S” 替代.
  • 由于太多乘客的 “Cabin” 数据缺失, 从所有数据中丢弃这个特征的值.
data = df.copy()
data["age"].fillna(df["age"].median(skipna=True), inplace=True)
data["embarked"].fillna(df['embarked'].value_counts().idxmax(), inplace=True)
data.drop('cabin', axis=1, inplace=True)

  
 
  • 1
  • 2
  • 3
  • 4
# 确认数据是否还包含缺失数据
data.isnull().sum()

  
 
  • 1
  • 2
pclass 1
survived 1
name 1
sex 1
age 0
sibsp 1
parch 1
ticket 1
fare 2
embarked 0
dtype: int64

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
#处理仍然存在缺失数据的情况
final.dropna(inplace=True)

  
 
  • 1
  • 2
# 预览调整过的数据
data.head()

  
 
  • 1
  • 2
pclass survived name sex age sibsp parch ticket fare embarked
0 1.0 1.0 Allen, Miss. Elisabeth Walton female 29.0000 0.0 0.0 24160 211.3375 S
1 1.0 1.0 Allison, Master. Hudson Trevor male 0.9167 1.0 2.0 113781 151.5500 S
2 1.0 0.0 Allison, Miss. Helen Loraine female 2.0000 1.0 2.0 113781 151.5500 S
3 1.0 0.0 Allison, Mr. Hudson Joshua Creighton male 30.0000 1.0 2.0 113781 151.5500 S
4 1.0 0.0 Allison, Mrs. Hudson J C (Bessie Waldo Daniels) female 25.0000 1.0 2.0 113781 151.5500 S

查看年龄在调整前后的分布

plt.figure(figsize=(15,8))
ax = df["age"].hist(bins=15, normed=True, stacked=True, color='teal', alpha=0.6)
df["age"].plot(kind='density', color='teal')
ax = data["age"].hist(bins=15, normed=True, stacked=True, color='orange', alpha=0.5)
data["age"].plot(kind='density', color='orange')
ax.legend(['Raw Age', 'Adjusted Age'])
ax.set(xlabel='Age')
plt.xlim(-10,85)
plt.show()

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9

在这里插入图片描述

[

2.4.1. 其它特征的处理

数据中的两个特征 “sibsp” (一同登船的兄弟姐妹或者配偶数量)与“parch”(一同登船的父母或子女数量)都是代表是否有同伴同行. 为了预防这两个特征具有多重共线性, 我们可以将这两个变量转为一个变量 “TravelAlone” (是否独自一人成行)

注: 多重共线性(multicollinearity)是指多变量线性回归中,变量之间由于存在高度相关关系而使回归估计不准确。比如虚拟变量陷阱(英语:Dummy variable trap)即有可能触发多重共线性问题。

## 创建一个新的变量'TravelAlone'记录是否独自成行, 丢弃“sibsp” (一同登船的兄弟姐妹或者配偶数量)与“parch”(一同登船的父母或子女数量)
data['TravelAlone']=np.where((data["sibsp"]+data["parch"])>0, 0, 1)
data.drop('sibsp', axis=1, inplace=True)
data.drop('parch', axis=1, inplace=True)

  
 
  • 1
  • 2
  • 3
  • 4

对类别变量(categorical variables)使用独热编码(One-Hot Encoding), 将字符串类别转换为数值

# 对 Embarked","Sex"进行独热编码, 丢弃 'name', 'ticket'
final =pd.get_dummies(data, columns=["embarked","sex"])
final.drop('name', axis=1, inplace=True)
final.drop('ticket', axis=1, inplace=True)

final.head()

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
pclass survived age fare TravelAlone embarked_C embarked_Q embarked_S sex_female sex_male
0 1.0 1.0 29.0000 211.3375 1 0 0 1 1 0
1 1.0 1.0 0.9167 151.5500 0 0 0 1 0 1
2 1.0 0.0 2.0000 151.5500 0 0 0 1 1 0
3 1.0 0.0 30.0000 151.5500 0 0 0 1 0 1
4 1.0 0.0 25.0000 151.5500 0 0 0 1 1 0

3. 数据分析

3.1. 年龄

plt.figure(figsize=(15,8))
ax = sns.kdeplot(final["age"][final.survived == 1], color="darkturquoise", shade=True)
sns.kdeplot(final["age"][final.survived == 0], color="lightcoral", shade=True)
plt.legend(['Survived', 'Died'])
plt.title('Density Plot of Age for Surviving Population and Deceased Population')
ax.set(xlabel='Age')
plt.xlim(-10,85)
plt.show()

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8

在这里插入图片描述

生还与遇难群体的分布相似, 唯一大的区别是生还群体中用一部分低年龄的乘客. 说明当时的人预先保留了孩子的生还机会.

3.2. 票价

plt.figure(figsize=(15,8))
ax = sns.kdeplot(final["fare"][final.survived == 1], color="darkturquoise", shade=True)
sns.kdeplot(final["fare"][final.survived == 0], color="lightcoral", shade=True)
plt.legend(['Survived', 'Died'])
plt.title('Density Plot of Fare for Surviving Population and Deceased Population')
ax.set(xlabel='Fare')
plt.xlim(-20,200)
plt.show()

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8

在这里插入图片描述

生还与遇难群体的票价分布差异比较大, 说明这个特征对预测乘客是否生还非常重要. 票价和仓位相关, 也许是仓位影响了逃生的效果, 我们接下来看仓位的分析.

3.3. 仓位

sns.barplot('pclass', 'survived', data=df, color="darkturquoise")
plt.show()

  
 
  • 1
  • 2

[外链图片转存失败(img-TbqcHxmW-1562946634662)(output_43_0.png)]
在这里插入图片描述
如我们所料, 一等舱的乘客生还几率最高.

3.4. 登船地点

sns.barplot('embarked', 'survived', data=df, color="teal")
plt.show()

  
 
  • 1
  • 2

在这里插入图片描述

从法国 Cherbourge 登录的乘客生还率最高

3.5. 是否独自成行

sns.barplot('TravelAlone', 'survived', data=final, color="mediumturquoise")
plt.show()

  
 
  • 1
  • 2

在这里插入图片描述

独自成行的乘客生还率比较低. 当时的年代, 大多数独自成行的乘客为男性居多.

3.6. 性别

sns.barplot('sex', 'survived', data=df, color="aquamarine")
plt.show()

  
 
  • 1
  • 2

在这里插入图片描述
很明显, 女性的生还率比较高

4. 使用Logistic Regression做预测

from sklearn.linear_model import LogisticRegression
from sklearn.model_selection import train_test_split
from sklearn.metrics import accuracy_score

# 使用如下特征做预测
cols = ["age","fare","TravelAlone","pclass","embarked_C","embarked_S","sex_male"] 

# 创建 X (特征) 和 y (类别标签)
X = final[cols]
y = final['survived']

# 将 X 和 y 分为两个部分
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=2) # 训练模型,  

model = LogisticRegression()
model.fit(X_train,y_train.values.reshape(-1,1))
# 根据模型, 以 X_test 为输入, 生成变量 y_pred
print('Train/Test split results:')
y_pred = model.predict(X_test)
print("准确率为 %2.3f" % accuracy_score(y_test, y_pred))


  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
Train/Test split results:
准确率为 0.817

  
 
  • 1
  • 2

文章来源: maoli.blog.csdn.net,作者:刘润森!,版权归原作者所有,如需转载,请联系作者。

原文链接:maoli.blog.csdn.net/article/details/95679249

【版权声明】本文为华为云社区用户转载文章,如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。