手把手教你用Python进行回归(附代码、学习资料)

本文介绍了线性回归、多项式回归及其局限性,重点讲解了样条回归的概念和实现,包括分段阶梯函数、基函数、分段多项式以及自然三次样条。通过Python代码示例,展示了样条回归如何处理非线性关系,提高模型预测能力。文章以工资预测数据集为例,对比了不同回归方法的效果,并探讨了如何选择和确定样条回归的节点数量。
摘要由CSDN通过智能技术生成

作者: GURCHETAN SINGH 

翻译:张逸

校对:丁楠雅

本文共5800字,建议阅读8分钟。
本文从线性回归、多项式回归出发,带你用Python实现样条回归。


我刚开始学习数据科学时,第一个接触到的算法就是线性回归。在把这个方法算法应用在到各种各样的数据集的过程中,我总结出了一些它的优点和不足。


首先,线性回归假设自变量和因变量之间存在线性关系,但实际情况却很少是这样。为了改进这个问题模型,我尝试了多项式回归,效果确实好一些(大多数情况下都是如此会改善)。但又有一个新问题:当数据集的变量太多的时候,用多项式回归很容易产生过拟合。



由于而且我建立的模型总是过于灵活,它可能在测试集上结果很好,但在那些“看不见的”数据上表现的就差强人意了。后来我看到另外一种称为样条回归的非线性方法---它将线性/多项式函数进行组合,用最终的结果来拟合数据。


在这篇文章中,我将会介绍线性回归、多项式回归的基本概念,然后详细说明关于样条回归的更多细节以及它的Python实现。


注:为了更好的理解本文中所提到的各种概念,你需要有线性回归和多项式回归的基础知识储备。这里有一些相关资料可以参考:


https://www.analyticsvidhya.com/blog/2015/08/comprehensive-guide-regression/


本文结构


  • 了解数据

  • 简单回顾线性回归

  • 多项式回归:对线性会回归的改进

  • 理解样条回归及其实现

    • 分段阶梯函数

    • 基函数

    • 分段多项式

    • 约束和样条

    • 三次样条和自然三次样条

    • 确定节点的数量和位置

    • 比较样条回归和多项式回归


了解数据


为了更好的理解这些概念,我们选择了工资预测数据集来做辅助说明。你可以在这儿下载:


https://drive.google.com/file/d/1QIHCTvHQIBpilzbNxGmbdEBEbmEkMd_K/view


这个数据集是从一本最近热门的书《Introduction to Statistical learning》(http://www-bcf.usc.edu/~gareth/ISL/ ISLR%20Seventh%20Printing.pdf)上摘取下来的。


我们的数据集包括了诸如ID、出生年份、性别、婚姻状况、种族、教育程度、职业、健康状况、健康保险和工资记录这些信息。为了详细解释样条回归,我们将只用年龄作为自变量来预测工资(因变量)。


让我们开始吧:


#导入需要的包

import pandas as pd

import numpy as np

import statsmodels.api as sm

import matplotlib.pyplot as plt

%matplotlib inline

#读入数据

data = pd.read_csv("Wage.csv")

data.head()


我们会得到这样的结果:



继续:


data_x = data['age']

data_y = data['wage']

#将数据划分为训练集和验证集

from sklearn.model_selection import train_test_split

train_x, valid_x, train_y, valid_y = train_test_split(data_x, data_y, test_size=0.33, random_state = 1)

#对年龄和工资的关系进行可视化

import matplotlib.pyplot as plt

plt.scatter(train_x, train_y, facecolor='None', edgecolor='k', alpha=0.3)plt.show()


我们会得到这样的图:



看到上边这个散点图,你会想到什么?这到底是代表正相关还是负相关?或者说根本没有联系?大家可以在下方的评论区说说自己的观点。


介绍线性回归


线性回归是预测模型中最简单同时应用最广泛的统计方法。它是用来解决基于回归任务的一种监督学习方法。


这种方法建立了自变量和因变量之间线性的关系,所以被称为线性回归。主要是一个线性方程,就像下边这个式子。可以这么理解:我们的特征就是一组带系数的自变量。



这个式子中,我们认为Y是因变量,X为自变量,所有的β都是系数。这些系数即为对应特征的权重,表示了每个特征的重要性。比如说:某个预测的结果高度依赖于诸多特征中的一个(X1),则意味着与其他所有特征相比,X1的系数(即权重)值会更高。


下面我们来试着理解一下只有一个特征的线性回归。即:只有一个自变量。它被称为简单线性回归。对应的式子是这样的:


好的,我可以为您提供一些关于使用Python代码实现Transformer的指导。 首先,您需要安装PyTorch和torchtext库。然后,您可以按照以下步骤实现Transformer模型: 1. 定义输入和输出的词汇表,并使用torchtext库加载数据集。 2. 定义Transformer模型的编码器和解码器部分。 3. 实现自注意力机制(self-attention)和前向神经网络(feed-forward network)。 4. 实现残差连接(residual connection)和层归一化(layer normalization)。 5. 定义Transformer模型的训练和评估过程。 下面是一个简单的示例代码,用于实现一个基本的Transformer模型: ```python import torch import torch.nn as nn import torch.optim as optim import torch.nn.functional as F from torchtext.datasets import TranslationDataset, Multi30k from torchtext.data import Field, BucketIterator # 定义输入和输出的词汇表 SRC = Field(tokenize='spacy', tokenizer_language='de', init_token='<sos>', eos_token='<eos>', lower=True) TRG = Field(tokenize='spacy', tokenizer_language='en', init_token='<sos>', eos_token='<eos>', lower=True) # 加载数据集 train_data, valid_data, test_data = Multi30k.splits(exts=('.de', '.en'), fields=(SRC, TRG)) SRC.build_vocab(train_data, min_freq=2) TRG.build_vocab(train_data, min_freq=2) # 定义Transformer模型的编码器和解码器部分 class Encoder(nn.Module): def __init__(self, input_dim, hid_dim, n_layers, n_heads, pf_dim, dropout, device): super().__init__() self.device = device self.tok_embedding = nn.Embedding(input_dim, hid_dim) self.pos_embedding = nn.Embedding(1000, hid_dim) self.layers = nn.ModuleList([EncoderLayer(hid_dim, n_heads, pf_dim, dropout, device) for _ in range(n_layers)]) self.dropout = nn.Dropout(dropout) self.scale = torch.sqrt(torch.FloatTensor([hid_dim])).to(device) def forward(self, src, src_mask): # src: [batch_size, src_len] # src_mask: [batch_size, 1, 1, src_len] batch_size = src.shape[0] src_len = src.shape[1] pos = torch.arange(0, src_len).unsqueeze(0).repeat(batch_size, 1).to(self.device) # pos: [batch_size, src_len] src = self.dropout((self.tok_embedding(src) * self.scale) + self.pos_embedding(pos)) for layer in self.layers: src = layer(src, src_mask) return src class EncoderLayer(nn.Module): def __init__(self, hid_dim, n_heads, pf_dim, dropout, device): super().__init__() self.self_attn_layer_norm = nn.LayerNorm(hid_dim) self.ff_layer_norm = nn.LayerNorm(hid_dim) self.self_attention = MultiHeadAttentionLayer(hid_dim, n_heads, dropout, device) self.positionwise_feedforward = PositionwiseFeedforwardLayer(hid_dim, pf_dim, dropout) self.dropout = nn.Dropout(dropout) def forward(self, src, src_mask):
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值