首页 > 其他分享 >线性回归的代码实现

线性回归的代码实现

时间:2023-11-18 16:00:35浏览次数:35  
标签:plt train 代码 self num 线性 theta data 回归

1.初始化步骤

import numpy as np
from utils.features import prepare_for_training

class LinearRegression:

    def __init__(self, data, labels, polynomial_degree=0, sinusoid_degree=0, normalize_data=True):
        """
        初始化线性回归模型对象。

        参数:
        - data: 输入数据集,每行表示一个样本,每列表示一个特征。
        - labels: 对应于输入数据集的标签。
        - polynomial_degree: 多项式特征的最高次数,默认为0,表示不使用多项式特征。
        - sinusoid_degree: 正弦特征的最高次数,默认为0,表示不使用正弦特征。
        - normalize_data: 是否对数据进行归一化,默认为True。

        初始化过程:
        1. 对输入数据进行预处理,包括多项式特征和正弦特征的处理,以及数据的归一化。
        2. 获取预处理后的数据、特征均值和标准差。
        3. 将预处理后的数据、标签,特征均值和标准差保存在对象的属性中。
        4. 获取预处理后数据的特征数量。
        5. 初始化参数矩阵theta为全零,其维度为(num_features, 1),其中num_features为特征数量。

        最终,LinearRegression对象被初始化为一个包含预处理信息和参数矩阵的线性回归模型。
        """
        # 1. 对数据进行预处理操作
        (data_processed,
         features_mean, 
         features_deviation) = prepare_for_training(data, polynomial_degree, sinusoid_degree, normalize_data=True)
         
        # 2. 将处理后的数据、标签以及预处理过程中得到的特征均值和标准差保存在对象的属性中
        self.data = data_processed
        self.labels = labels
        self.features_mean = features_mean
        self.features_deviation = features_deviation
        self.polynomial_degree = polynomial_degree
        self.sinusoid_degree = sinusoid_degree
        self.normalize_data = normalize_data
        
        # 3. 获取特征的数量,并初始化参数矩阵theta为全零
        num_features = self.data.shape[1]
        self.theta = np.zeros((num_features, 1))

2.模型的训练和梯度下降的过程

    def train(self, alpha, num_iterations=500):
        """
        训练模块,执行梯度下降。

        参数:
        - alpha: 学习率,控制每次参数更新的步长。
        - num_iterations: 迭代次数,默认为500。

        返回:
        - 训练后的参数矩阵theta
        - 每次迭代损失值的历史记录
        """
        # 执行梯度下降,获取损失值的历史记录
        cost_history = self.gradient_descent(alpha, num_iterations)
        # 返回训练后的参数矩阵和损失值的历史记录
        return self.theta, cost_history

    def gradient_descent(self, alpha, num_iterations):
        """
        实际迭代模块,会迭代num_iterations次。

        参数:
        - alpha: 学习率,控制每次参数更新的步长。
        - num_iterations: 迭代次数。

        返回:
        - 每次迭代损失值的历史记录
        """
        cost_history = []  # 用于存储每次迭代的损失值
        for _ in range(num_iterations):
            self.gradient_step(alpha)  # 执行一次梯度下降参数更新
            cost_history.append(self.cost_function(self.data, self.labels))  # 计算并记录当前损失值
        return cost_history

    def gradient_step(self, alpha):    
        """
        梯度下降参数更新计算方法,注意是矩阵运算。

        参数:
        - alpha: 学习率,控制每次参数更新的步长。
        """
        num_examples = self.data.shape[0]  # 样本数量
        prediction = LinearRegression.hypothesis(self.data, self.theta)  # 计算模型的预测值
        delta = prediction - self.labels  # 计算预测值与实际值的差异
        theta = self.theta  # 获取当前的参数矩阵
        theta = theta - alpha * (1/num_examples) * (np.dot(delta.T, self.data)).T  # 更新参数矩阵
        self.theta = theta  # 将更新后的参数矩阵保存在对象中

    def cost_function(self, data, labels):
        """
        损失计算方法。

        参数:
        - data: 输入数据集。
        - labels: 对应于输入数据集的标签。

        返回:
        - 损失值
        """
        num_examples = data.shape[0]  # 样本数量
        delta = LinearRegression.hypothesis(data, self.theta) - labels  # 计算预测值与实际值的差异
        cost = (1/2) * np.dot(delta.T, delta) / num_examples  # 计算损失值
        return cost[0][0]  # 返回损失值

这段代码包含了训练模块、实际迭代模块、梯度下降参数更新计算方法和损失计算方法。在 train 方法中,通过调用 gradient_descent 方法执行梯度下降,并返回训练后的参数矩阵和损失值的历史记录。在 gradient_descent 方法中,通过循环执行梯度下降的迭代,并记录每次迭代的损失值。在 gradient_step 方法中,实现了梯度下降的参数更新计算。在 cost_function 方法中,计算了损失值。

3.模型的训练和预测

import numpy as np
import pandas as pd
import matplotlib.pyplot as plt

# 导入自定义的线性回归模块
from linear_regression import LinearRegression

# 从CSV文件中读取数据
data = pd.read_csv('../data/world-happiness-report-2017.csv')

# 得到训练和测试数据
train_data = data.sample(frac=0.8)
test_data = data.drop(train_data.index)

# 选择输入和输出参数的列名
input_param_name = 'Economy..GDP.per.Capita.'
output_param_name = 'Happiness.Score'

# 提取训练数据和测试数据的特征和标签
x_train = train_data[[input_param_name]].values
y_train = train_data[[output_param_name]].values

x_test = test_data[input_param_name].values
y_test = test_data[output_param_name].values

# 绘制训练和测试数据的散点图
plt.scatter(x_train, y_train, label='Train data')
plt.scatter(x_test, y_test, label='Test data')
plt.xlabel(input_param_name)
plt.ylabel(output_param_name)
plt.title('Happiness vs. GDP per Capita')
plt.legend()
plt.show()

# 设置迭代次数和学习率
num_iterations = 500
learning_rate = 0.01

# 初始化线性回归模型并进行训练
linear_regression = LinearRegression(x_train, y_train)
(theta, cost_history) = linear_regression.train(learning_rate, num_iterations)

# 打印训练前和训练后的损失值
print('开始时的损失:', cost_history[0])
print('训练后的损失:', cost_history[-1])

# 绘制损失函数的迭代曲线
plt.plot(range(num_iterations), cost_history)
plt.xlabel('迭代次数')
plt.ylabel('损失值')
plt.title('梯度下降过程中损失函数的变化')
plt.show()

# 进行额外的预测
predictions_num = 100
x_predictions = np.linspace(x_train.min(), x_train.max(), predictions_num).reshape(predictions_num, 1)
y_predictions = linear_regression.predict(x_predictions)

# 绘制预测结果
plt.scatter(x_train, y_train, label='Train data')
plt.scatter(x_test, y_test, label='Test data')
plt.plot(x_predictions, y_predictions, 'r', label='Prediction')
plt.xlabel(input_param_name)
plt.ylabel(output_param_name)
plt.title('Happiness vs. GDP per Capita with Prediction')
plt.legend()
plt.show()

 

标签:plt,train,代码,self,num,线性,theta,data,回归
From: https://www.cnblogs.com/wzbzk/p/17840637.html

相关文章

  • 代码随想录算法训练营第六天 |● 哈希表理论基础 ● 242.有效的字母异位词 ● 349.
    今日学习的文章链接和视频链接https://programmercarl.com/哈希表理论基础.html242.有效的字母异位词varisAnagram=function(s,t){if(s.length!==t.length)returnfalseletmap=newMap();for(letcharofs){if(!map.get(char)){......
  • L1-6 吉老师的回归 (15 分)(C/C++)
    输入样例1:51L1-1isaqiandaoproblem.L1-2isso...easy.L1-3isEasy.L1-4isqianDao.Wow,suchL1-5,soeasy.输出样例1:L1-4isqianDao.输入样例2:54L1-1isa-qiandaoproblem.L1-2issoeasy.L1-3isEasy.L1-4isqianDao.Wow,suchL1-5,so!!easy.输出样例......
  • 2023版 STM32实战1 LED灯驱动(电路与代码都讲解)
    电路图常规画法(带限流电阻计算公式)设LED电流为20mA(统一单位为0.02A)电压为3.3V限流电阻=(电源电压-负载正向工作电压)/工作电流限流电阻=(5V-3.3V)/0.02mA=1.7/V0.02A=85R省事画法(直接用IO输出)代码(直接拷贝使用)找对引脚!!!这是一个LED闪烁的demo为了新手方便我直接都写在了main.c......
  • 使用 ABAP + OLE 消费 Windows DLL 文件里的代码和服务
    在SAPABAP中,我们可以使用OLE(ObjectLinkingandEmbedding)技术来实现对WindowsDLL文件的代码和服务的消费。以下是一个详细的解决方案:首先,我们需要明确OLE技术在ABAP中的应用。OLE是由微软开发的一种技术,它允许对象(即应用程序功能)被嵌入到其他应用程序中。在ABA......
  • 2023版 STM32实战1 LED灯驱动(电路与代码都讲解)
    电路图常规画法(带限流电阻计算公式) 设LED电流为20mA(统一单位为0.02A)电压为3.3V限流电阻=(电源电压-负载正向工作电压)/工作电流限流电阻=(5V-3.3V)/0.02mA=1.7/V0.02A=85R省事画法(直接用IO输出)  代码(直接拷贝使用)找对引脚!!!这是一个LED闪烁的demo为了新手方便我......
  • 代码随想训练营第三十七天(Python)| 738.单调递增的数字、968.监控二叉树
    738.单调递增的数字classSolution:defmonotoneIncreasingDigits(self,n:int)->int:#主要思路当前数字比前面数字小时。前面数字-1,当前数字变2为9str_n=str(n)foriinrange(len(str_n)-1,0,-1):ifstr_n[i]<str_n[......
  • 代码训练营第三十八天(Python)| 509. 斐波那契数、70. 爬楼梯、746. 使用最小花费爬楼梯
    509.斐波那契数1、动态规划classSolution:deffib(self,n:int)->int:ifn<=1:returnn#dp[i]代表第i个数的斐波那契值dp=[0]*(n+1)dp[0]=0dp[1]=1foriinrange(2,n+1):......
  • 【Node.js】 - 概念 fs path模块 压缩HTML代码
    一、概念Node.js是一个跨平台javaScript运行环境,使开发者可以搭建服务器端的JavaScript应用程序作用:1.编写数据接口,提供网页资源浏览功能等等2.前端工程化二、什么是前端工程化开发项目直到上线,过程中集成的所有工具和技术Node.js是前端工程化的基础(因为Node.js可以主动读取前端代......
  • 电脑控制多台手机类软件开发基础代码!
    随着移动设备的普及,越来越多的应用需要同时控制多台手机,例如,在营销推广、教育和培训、现场活动等领域,往往需要同时对多台手机进行操作,为了满足这一需求,开发者们开发出了各种电脑控制多台手机类的软件,本文将分享这类软件开发的基础代码,帮助您更好地理解其原理和实现方式。一、蓝牙连......
  • 定制开发手机软件常见代码!
    随着智能手机的普及,手机应用开发已成为当今IT行业的热门领域,越来越多的企业和个人选择定制开发手机应用,以满足自身的业务需求,在开发过程中,一些常见的代码和技巧是必不可少的,本文将分享一些定制开发手机APP的常见代码和技巧,帮助您更好地进行开发。一、使用Kotlin语言的优势Kotlin是......