笔记——线性回归的实现

1. 简单线性回归

import numpy as np
from metrics import r2_score
class SimpleLinearRegression1:
    def __init__(self):
        """初始化SimpleLinearRegression模型"""
        self.a_=None
        self.b_=None
    def fit(self,x_train,y_train):
        """根据训练数据集x_train,y_train训练SimpleLinearRegression模型"""
        assert x_train.ndim==1,"只能解决单一特征数据"
        assert len(x_train)==len(y_train),\
        "x和y的个数必须相等"
        x_mean=np.mean(x_train)
        y_mean=np.mean(y_train)

        num = 0.0
        d = 0.0
        for x_i, y_i in zip(x_train, y_train):
            num += (x_i - x_mean) * (y_i - y_mean)
            d += (x_i - x_mean) ** 2

        self.a_=num/d
        self.b_=y_mean-self.a_*x_mean

        return self
    def predict(self,x_predict):
        """给定预测数据集x_predict,返回表示x_predict的结果向量"""
        assert x_predict.ndim==1,"x_predict只能是一维数组"
        assert self.a_ is not None and self.b_ is not None,\
            "在预测之前必须先训练得到参数a,b"
        return np.array([self._predict(x) for x in x_predict])

    def _predict(self,x_single):
        """给定单个预测数据x_single,返回预测结果"""
        return self.a_*x_single+self.b_
    def __repr__(self):
        return "SimpleLinearRegression1()"

class SimpleLinearRegression2:
    def __init__(self):
        """初始化SimpleLinearRegression模型"""
        self.a_=None
        self.b_=None
    def fit(self,x_train,y_train):
        """根据训练数据集x_train,y_train训练SimpleLinearRegression模型"""
        assert x_train.ndim==1,"只能解决单一特征数据"
        assert len(x_train)==len(y_train),\
        "x和y的个数必须相等"
        x_mean=np.mean(x_train)
        y_mean=np.mean(y_train)

        num = (x_train - x_mean).dot(y_train - y_mean)
        d = (x_train - x_mean).dot(x_train - x_mean)

        self.a_ = num / d
        self.b_ = y_mean - self.a_ * x_mean

        return self
    def predict(self,x_predict):
        """给定预测数据集x_predict,返回表示x_predict的结果向量"""
        assert x_predict.ndim==1,"x_predict只能是一维数组"
        assert self.a_ is not None and self.b_ is not None,\
            "在预测之前必须先训练得到参数a,b"
        return np.array([self._predict(x) for x in x_predict])

    def _predict(self,x_single):
        """给定单个预测数据x_single,返回预测结果"""
        return self.a_*x_single+self.b_

    def score(self,x_test,y_test):
        "计算当前模型的准确度"
        y_predict=self.predict(x_test)
        return r2_score(y_test,y_predict)

    def __repr__(self):
        return "SimpleLinearRegression2()"

2. 线性回归

import numpy as np
from metrics import r2_score

class LinearRegression:
    def __int__(self):
        "初始化"
        self.coef_=None
        self.interception_=None
        self._theta=None

    def fit_normal(self,X_train,y_train):
        assert X_train.shape[0]==y_train.shape[0],\
            "必须相等"

        X_b=np.hstack([np.ones((len(X_train),1)),X_train])
        self._theta=np.linalg.inv(X_b.T.dot(X_b)).dot(X_b.T).dot(y_train);

        self.interception_=self._theta[0]
        self.coef_=self._theta[1:]

        return self

    def predict(self,X_predict):
        assert self.interception_ is not None and self.coef_ is not None,\
            "must fit before predict!"
        assert X_predict.shape[1]==len(self.coef_),\
            "X_predict的特征数量必须等于X_train"
        X_b = np.hstack([np.ones((len(X_predict), 1)), X_predict])
        return X_b.dot(self._theta)

    def score(self,X_test,y_test):

        y_predict=self.predict(X_test)
        return r2_score(y_test,y_predict)

    def __repr__(self):
        return "LinearRegression()"

3.线性回归2:最小二乘法

class LinearRegression:
    """最小二乘法实现"""
    def fit(self,X,y):
        #注意:X必须是完整的矩阵,通过拷贝X,避免X只是数组对象的一部分(进行了切片)
        X=np.asmatrix(X.copy())
        #y是一维,可以不用进行拷贝,因为进行矩阵运算,必须转化为二维矩阵
        y=np.asmatrix(y).reshape(-1,1)
        #通过最小二乘公式,求解出最佳的权重值
        self.w_=(X.T*X).I*X.T*y
        
    def predict(self,X):
        
        X=np.asmatrix(X.copy())
        result=X*self.w_
        #将矩阵转化为数组,使用ravel()进行扁平化处理
        return np.array(result).ravel()
        

4.线性回归3:梯度下降

class LinearRegression:
    """线性回归算法:梯度下降法实现"""
    def __init__(self,alpha,times):
        """alpha: float 学习率。用来控制步长(权重调整的幅度)
           times:int 循环迭代的次数"""
        self.alpha=alpha
        self.times=times
        
    def fit(self,X,y):
        
        X=np.asarray(X)
        y=np.asarray(y)
        #创建权重的向量,初始值为0(或其他值),长度比特征数量多1(多出来的值是截距)
        self.w_=np.zeros(1+X.shape[1])
        #创建损失列表,用来保存每次迭代过后的损失值。损失计算:(预测值-真实值)的平方和/2
        self.loss_=[]
        #进行循环迭代,调整权重值,使损失函数的值不断减小。
        for i in range(self.times):
            #计算预测值
            y_hat=np.dot(X,self.w_[1:])+self.w_[0]
            #计算真实值和预测值之间的差距
            error=y-y_hat
            #将损失值加入到损失列表中
            self.loss_.append(np.sum(error**2)/2)
            # 根据差距调整权重w_,根据公式,调整为:权重(j)=权重(j)+学习率*sum((y-y_hat)*x(j))
            self.w_[0]+=self.alpha*np.sum(error)#截距
            self.w_[1:]+=self.alpha*np.dot(X.T,error)#特征属性
            
    def predict(self,X):
        
        X=np.asarray(X)
        result=np.dot(X,self.w_[1:])+self.w_[0]
        
        return result
    
  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值