机器学习:逻辑回归

目录

一、理论知识

1、Sigmoid激活函数

2、逻辑回归模型

3、损失函数(交叉熵损失)

4、梯度计算

5、梯度下降

二、代码实现

1、导入Python包

2、利用sklearn构造二分类数据集

3、定义sigmoid激活函数

4、定义前向传播函数、损失函数、反向传播函数

5、定义并初始化权重参数 W 和 b

6、划分训练集和测试集

7、模型训练

8、模型测试 


一、理论知识

1、Sigmoid激活函数

Sigmoid激活函数将实数输入映射到(0, 1)区间,可用于二分类任务,其数学定义如下:

f(x) = \frac{1}{1+e^{-x}}

其函数图像为:

其导数为:

f'(x) =\frac{1}{1+e^{-x}} \cdot (1 - \frac{1}{1+e^{-x}}) = f(x) \cdot (1-f(x)) 

2、逻辑回归模型

\hat{Y} = \sigma(XW+b)

其中,X \in \mathbb{R}^{N \times M}表示输入,\hat{Y} \in \mathbb{R}^{N \times 1}表示输出,W \in \mathbb{R}^{M \times 1}b \in \mathbb{R}^{1 \times 1}表示可学习的权重参数,\sigma表示Sigmoid激活函数。逻辑回归模型与线性回归模型的区别在于逻辑回归模型多了一个激活函数。

3、损失函数(交叉熵损失)

L = -\frac{1}{N} \sum_{i=1}^{N} y_i \cdot log\hat{y}_i + (1-y_i) \cdot log(1-\hat{y}_i)

其中,y_i \in \{0, 1\}\hat{y}_i \in (0, 1)。当y_i = 1时,(1-y_i) \cdot log(1-\hat{y}_i) = 0\hat{y} = 1损失达到最小。同样地,当y_i = 0时,y_i \cdot log\hat{y}_i = 0\hat{y} = 0损失达到最小。

4、梯度计算

\frac{\partial L}{\partial W} = \frac{1}{N} \cdot X^T(\hat{Y}-Y)

\frac{\partial L}{\partial b} = \frac{1}{N} \cdot (\hat{Y}-Y)

注:梯度计算的结果与线性回归模型的结果一致。

5、梯度下降

W_{new} = W_{old} - \alpha \cdot \frac{\partial L}{\partial W}

b_{new} = b_{old} - \alpha \cdot \frac{\partial L}{\partial b}

其中,\alpha是梯度下降步长,又称学习率。多次迭代执行前向传播(计算映射函数)和反向传播(梯度计算+梯度下降),损失函数最终收敛至局部最优解。

二、代码实现

1、导入Python包

import numpy as np
import matplotlib.pyplot as plt
from sklearn.datasets import make_blobs
from sklearn.model_selection import train_test_split
 
plt.rcParams['font.sans-serif'] = ['Times New Roman']

2、利用sklearn构造二分类数据集

data, target = make_blobs(n_samples=1000, n_features=2, centers=2, random_state=2024)

plt.figure(dpi=100)
plt.scatter(data[:,0], data[:,1], c=target)

3、定义sigmoid激活函数

def sigmoid(z):
    return 1/(1+np.exp(-z))

4、定义前向传播函数、损失函数、反向传播函数

def forward(X, weights, bias):
    Y_hat = sigmoid(np.dot(X, weights) + bias)
    return Y_hat

def Loss_fuction(Y, Y_hat):
    N = Y.shape[0]
    cost = -1 / N * np.sum(Y * np.log(Y_hat) + (1 - Y) * np.log(1 - Y_hat))
    return cost

def backward(X, Y, Y_hat, weights, bias, lr):
    # 梯度计算
    N = Y.shape[0]
    dw = 1 / N * np.dot(X.T, (Y_hat - Y))
    db = 1 / N * np.sum(Y_hat - Y)

    # 权重更新
    weights -= lr * dw
    bias -= lr * db
    return weights, bias

5、定义并初始化权重参数 W 和 b

weights = np.zeros((2, 1))
bias = 0

6、划分训练集和测试集

X = data
Y = target[:,None]
X_train, X_test, Y_train, Y_test = train_test_split(X, Y, test_size=0.2, random_state=2024)
print(X_train.shape, X_test.shape, Y_train.shape, Y_test.shape)

7、模型训练

lr = 0.01 # 学习率
epochs = 1000  # 迭代次数
train_loss = []
for _ in range(epochs):
    # 前向传播
    Y_hat = forward(X_train, weights, bias)
 
    # 损失计算
    loss = Loss_fuction(Y_train, Y_hat)
    train_loss.append(loss)
 
    # 反向传播
    weights, bias = backward(X_train, Y_train, Y_hat, weights, bias, lr)

plt.figure(dpi=100)
plt.plot(train_loss)
plt.xlabel("Epoch")
plt.ylabel("Loss")
plt.title("Training Loss")
plt.show()

8、模型测试 

threshold = 0.5  # 判断正负类的阈值

y_predict = forward(X_test, weights, bias)
print(f"Test ACC: {np.mean((y_predict>threshold) == Y_test)}")

Test ACC: 1.0

  • 5
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值