pytorch深度学习实践(刘二大人)课后作业——Titanic数据集分析预测

一、课后作业

构造分类器对Titanic数据集进行预测

1.数据集预处理

(1)数据集下载与分析

下载地址:https://www.kaggle.com/c/titanic/data

导入必要的包,并查看训练集、测试集前五行数据

import torch
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns   #依赖库numpy、pandas、matlibplot、scipy都要安装

from torch.utils.data import Dataset   
from torch.utils.data import DataLoader 

train_data = pd.read_csv('D:\\test\\pytorch\\datasets\\titanic\\train.csv')
test_data = pd.read_csv('D:\\test\\pytorch\\datasets\\titanic\\test.csv')

print(train_data.head(5))
print(test_data.head(5))

在jupyter中运行结果如下:(此图展示的数据为训练集数据,测试集大家可以自行查看)

可以看到数据共有12列,具体包括:

:乘客编号(不重要)

Survived:生还情况,1为生还0则相反,也是需要预测的值;测试集数据不包含此列

Pclass:票务等级,分1、2、3级

Name:乘客姓名(不重要)

Sex:乘客性别,male、female,可考虑转换成0,1让模型进行学习

Age:年龄

SibSp:兄弟姐妹及配偶的数量

Parch:父母及子女的数量

Ticket:船票号码(不重要)

Fare:票价

Cabin:船舱

Embarked:登船港 C = Cherbourg, Q = Queenstown, S = Southampton

初步筛选出上述加粗字体特征数据进行后续的模型训练,舍弃passengerID、Name、Ticket

(2)数据清洗和整理

查看数据信息:

train_data.info()
test_data.info()

可以看到训练集数据量为891,其中Age、Cabin、Embarked特征有缺失。Age缺失较少,可以考虑采取中位数填充;Cabin缺失较多,舍弃此数据;Embarked缺失只有2个,可以考虑众数填充;

测试集数据量为418,其中Age、Cabin、Fare特征有缺失。处理方式与训练集相同,Age、Fare考虑采用中位数填充,Cabin舍弃。

#特征选择
y = train_data['Survived']  #真值
train_data.drop('Survived', axis=1, inplace=True) #.drop()用于删除指定行/列;
train_data.drop('PassengerId', axis=1, inplace=True) #axis=1表示列操作,不指定则默认为行操作
train_data.drop('Name', axis=1, inplace=True) #inplace=True表示就地修改,不设置则返回一个新的DataFrame
train_data.drop('Ticket', axis=1, inplace=True)
train_data.drop('Cabin', axis=1, inplace=True)

ID = test_data['PassengerId'] #记录测试集ID用于后续生成结果csv文件
test_data.drop('PassengerId', axis=1, inplace=True)
test_data.drop('Name', axis=1, inplace=True)
test_data.drop('Ticket', axis=1, inplace=True)
test_data.drop('Cabin', axis=1, inplace=True)

#缺失值填充
train_data['Age'].fillna(train_data.Age.median(), inplace=True)
mode_Embarked = train_data['Embarked'].mode()[0]#计算Embark列的众数,因为可能包含多个众数,因此用[0]索引获取第一个
train_data['Embarked'].fillna(mode_Embarked, inplace=True) 
test_data['Age'].fillna(test_data.Age.median(), inplace=True)
test_data['Fare'].fillna(test_data.Fare.median(), inplace=True)

#分类型数据转化
d1={'male':0,'female':1}
d2={'S':1,'C':2,'Q':3} 
train_data['Sex']=train_data['Sex'].map(d1)
train_data['Embarked']=train_data['Embarked'].map(d2)
test_data['Sex']=test_data['Sex'].map(d1)
test_data['Embarked']=test_data['Embarked'].map(d2)

(3)Dataset&Dataloader

#Dataset and DataLoader
class train_TitanicDataset(Dataset):  
    def __init__(self):
        self.x_data = torch.from_numpy(x_train)
        self.y_data = torch.from_numpy(y_train).unsqueeze(1)  #得到的是一维张量,记得转成矩阵(列向量)
        self.len = x_train.shape[0]

    def __getitem__(self, index):   
        return self.x_data[index], self.y_data[index]

    def __len__(self):  
        return self.len

train_dataset = train_TitanicDataset()
train_loader = DataLoader(dataset=train_dataset,
                          batch_size=32,
                          shuffle=True,
                          num_workers=0)  

2.模型搭建及训练

搭了个五层的神经网络,代码和课上的差不多

#Model
class Model(torch.nn.Module):
    def __init__(self):
        super(Model, self).__init__()
        self.linear1 = torch.nn.Linear(7, 16)
        self.linear2 = torch.nn.Linear(16, 8)
        self.linear3 = torch.nn.Linear(8, 6)
        self.linear4 = torch.nn.Linear(6, 4)
        self.linear5 = torch.nn.Linear(4, 1)
        self.sigmoid = torch.nn.Sigmoid()

    def forward(self, x):
        x = self.sigmoid(self.linear1(x))
        x = self.sigmoid(self.linear2(x))
        x = self.sigmoid(self.linear3(x))
        x = self.sigmoid(self.linear4(x))
        x = self.sigmoid(self.linear5(x))
        return x 

model = Model()
criterion = torch.nn.BCELoss(size_average=True)
optimizer = torch.optim.Adam(model.parameters(), lr=0.001)
scheduler = torch.optim.lr_scheduler.StepLR(optimizer, step_size=20, gamma=0.7)  #学习率衰减,每过20epoch变为原来的0.7倍

epoch_list = []
loss_list = []


#Training
for epoch in range(100):
    for i, data in enumerate(train_loader, 0):  #0表示index从0开始读入,train_loader拿出的(x,y)元组放在data里,自动转tensor
        #1.prepare data
        inputs, labels = data  
        inputs = inputs.to(torch.float32)
        #2.forward
        y_pred = model(inputs)
        loss = criterion(y_pred.float(), labels.float())
        #3.backward
        optimizer.zero_grad()
        loss.backward()
        #4.update
        optimizer.step()
    scheduler.step()
    epoch_list.append(epoch)
    loss_list.append(loss.item())
    # print(epoch, loss.item())

plt.plot(epoch_list, loss_list)
plt.grid(True)
plt.xlabel('Epoch')
plt.ylabel('loss')
plt.savefig('train_loss')
plt.show()

3.预测及储存结果

#Predict
x_test = torch.from_numpy(x_test)
y_test_pred = model(x_test.to(torch.float32))
pred = y_test_pred.detach().numpy()
pred = pred.astype(int)  #官方csv文件是int格式,转化一下,否则提交得分是0
for i in range(len(pred)):
    if pred[i] > 0.5:
        pred[i] = 1
    else:
        pred[i] = 0
#print(pred)

#存储预测结果
df = pd.DataFrame(columns=['PassengerId','Survived'])
df['PassengerId']=ID
df['Survived']=pred
df.to_csv('pred_result.csv', index=False)

 loss曲线:

官网得分:

 我这个作业效果还不是很好,分数也不高,包括loss曲线也长得很奇怪,但是我只想完整地把作业完成一遍,不想继续做了hhhhhh大家可以自行搭建模型调整超参数,刷刷分~

数据预处理部分参考:Python数据分析案例08——预测泰坦尼克号乘员的生存(机器学习全流程)_泰坦尼克号生存预测python-CSDN博客

  • 23
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值