首页 > 编程语言 >【深度学习】Logistic回归算法和向量化编程。全md文档笔记(代码文档已分享)

【深度学习】Logistic回归算法和向量化编程。全md文档笔记(代码文档已分享)

时间:2024-02-24 23:01:41浏览次数:25  
标签:dz md frac train 文档 Logistic dw np dJ

本系列文章md笔记(已分享)主要讨论深度学习相关知识。可以让大家熟练掌握机器学习基础,如分类、回归(含代码),熟练掌握numpy,pandas,sklearn等框架使用。在算法上,掌握神经网络的数学原理,手动实现简单的神经网络结构,在应用上熟练掌握TensorFlow框架使用,掌握神经网络图像相关案例。具体包括:TensorFlow的数据流图结构,神经网络与tf.keras,卷积神经网络(CNN),商品物体检测项目介绍,YOLO与SSD,商品检测数据集训练和模型导出与部署。

完整笔记代码请移步:

请移步这里获取文档和代码

感兴趣的小伙伴可以自取哦,欢迎大家点赞转发~


共 9 章,60 子模块

TensorFlow介绍

说明TensorFlow的数据流图结构
应用TensorFlow操作图
说明会话在TensorFlow程序中的作用
应用TensorFlow实现张量的创建、形状类型修改操作
应用Variable实现变量op的创建
应用Tensorboard实现图结构以及张量值的显示
应用tf.train.saver实现TensorFlow的模型保存以及加载
应用tf.app.flags实现命令行参数添加和使用
应用TensorFlow实现线性回归

1.2 神经网络基础

学习目标

  • 目标

    • 知道逻辑回归的算法计算输出、损失函数
    • 知道导数的计算图
    • 知道逻辑回归的梯度下降算法
    • 知道多样本的向量计算
  • 应用

    • 应用完成向量化运算
    • 应用完成一个单神经元神经网络的结构

1.2.1 Logistic回归

1.2.1.1 Logistic回归

逻辑回归是一个主要用于二分分类类的算法。那么逻辑回归是给定一个xxx, 输出一个该样本属于1对应类别的预测概率y^=P(y=1x)\hat{y}=P(y=1|x)​y​^​​=P(y=1∣x)。

Logistic 回归中使用的参数如下:

eze^{-z}e​−z​​的函数如下

例如:

损失计算过程

1.2.1.2 逻辑回归损失函数

损失函数(loss function)用于衡量预测结果与真实值之间的误差。最简单的损失函数定义方式为平方差损失:

L(y^,y)=12(y^y)2L(\hat{y},y) = \frac{1}{2}(\hat{y}-y)^2L(​y​^​​,y)=​2​​1​​(​y​^​​−y)​2​​

逻辑回归一般使用L(y^,y)=(ylogy^)(1y)log(1y^)L(\hat{y},y) = -(y\log\hat{y})-(1-y)\log(1-\hat{y})L(​y​^​​,y)=−(ylog​y​^​​)−(1−y)log(1−​y​^​​)

该式子的理解:

  • 如果y=1,损失为logy^- \log\hat{y}−log​y​^​​,那么要想损失越小,y^\hat{y}​y​^​​的值必须越大,即越趋近于或者等于1
  • 如果y=0,损失为1log(1y^)1\log(1-\hat{y})1log(1−​y​^​​),那么要想损失越小,那么y^\hat{y}​y​^​​的值越小,即趋近于或者等于0

损失函数是在单个训练样本中定义的,它衡量了在单个训练样本上的表现。代价函数(cost function)衡量的是在全体训练样本上的表现,即衡量参数 w 和 b 的效果,所有训练样本的损失平均值

J(w,b)=1mi=1mL(y^(i),y(i))J(w,b) = \frac{1}{m}\sum_{i=1}mL(\hat{y},y^{(i)})J(w,b)=​m​​1​​∑​i=1​m​​L(​y​^​​​(i)​​,y​(i)​​)

1.2.2 梯度下降算法

目的:使损失函数的值找到最小值

方式:梯度下降

函数的梯度(gradient)指出了函数的最陡增长方向。梯度的方向走,函数增长得就越快。那么按梯度的负方向走,函数值自然就降低得最快了。模型的训练目标即是寻找合适的 w 与 b 以最小化代价函数值。假设 w 与 b 都是一维实数,那么可以得到如下的 J 关于 w 与 b 的图:

可以看到,成本函数 J 是一个凸函数,与非凸函数的区别在于其不含有多个局部最低。

参数w和b的更新公式为:

w:=wαdJ(w,b)dww := w - \alpha\frac{dJ(w, b)}{dw}w:=w−α​dw​​dJ(w,b)​​,b:=bαdJ(w,b)dbb := b - \alpha\frac{dJ(w, b)}{db}b:=b−α​db​​dJ(w,b)​​

注:其中 α 表示学习速率,即每次更新的 w 的步伐长度。当 w 大于最优解 w′ 时,导数大于 0,那么 w 就会向更小的方向更新。反之当 w 小于最优解 w′ 时,导数小于 0,那么 w 就会向更大的方向更新。迭代直到收敛。

通过平面来理解梯度下降过程:

1.2.3 导数

理解梯度下降的过程之后,我们通过例子来说明梯度下降在计算导数意义或者说这个导数的意义。

1.2.3.1 导数

导数也可以理解成某一点处的斜率。斜率这个词更直观一些。

  • 各点处的导数值一样

我们看到这里有一条直线,这条直线的斜率为4。我们来计算一个例子

例:取一点为a=2,那么y的值为8,我们稍微增加a的值为a=2.001,那么y的值为8.004,也就是当a增加了0.001,随后y增加了0.004,即4倍

那么我们的这个斜率可以理解为当一个点偏移一个不可估量的小的值,所增加的为4倍。

可以记做f(a)da\frac{f(a)}{da}​da​​f(a)​​或者ddaf(a)\frac{d}{da}f(a)​da​​d​​f(a)

  • 各点的导数值不全一致

例:取一点为a=2,那么y的值为4,我们稍微增加a的值为a=2.001,那么y的值约等于4.004(4.004001),也就是当a增加了0.001,随后y增加了4倍

取一点为a=5,那么y的值为25,我们稍微增加a的值为a=5.001,那么y的值约等于25.01(25.010001),也就是当a增加了0.001,随后y增加了10倍

可以得出该函数的导数2为2a。

  • 更多函数的导数结果
函数 导数
f(a)=a2f(a) = a^2f(a)=a​2​​ 2a2a2a
f(a)=a3f(a)=a^3f(a)=a​3​​ 3a23a^23a​2​​
f(a)=ln(a)f(a)=ln(a)f(a)=ln(a) 1a\frac{1}{a}​a​​1​​
f(a)=eaf(a) = e^af(a)=e​a​​ eae^ae​a​​
σ(z)=11+e−z\sigma(z) = \frac{1}{1+e^{-z}}σ(z)=​1+e​−z​​​​1​​ σ(z)(1−σ(z))\sigma(z)(1-\sigma(z))σ(z)(1−σ(z))
g(z)=tanh(z)=ez−e−zez+e−zg(z) = tanh(z) = \frac{e^z - e{-z}}{ez + e^{-z}}g(z)=tanh(z)=​e​z​​+e​−z​​​​e​z​​−e​−z​​​​ 1−(tanh(z))2=1−(g(z))21-(tanh(z))2=1-(g(z))21−(tanh(z))​2​​=1−(g(z))​2​​

1.2.3.2 导数计算图

那么接下来我们来看看含有多个变量的到导数流程图,假设J(a,b,c)=3(a+bc)J(a,b,c) = 3{(a + bc)}J(a,b,c)=3(a+bc)

我们以下面的流程图代替

这样就相当于从左到右计算出结果,然后从后往前计算出导数

  • 导数计算

问题:那么现在我们要计算J相对于三个变量a,b,c的导数?

假设b=4,c=2,a=7,u=8,v=15,j=45

  • dJdv=3\frac{dJ}{dv}=3​dv​​dJ​​=3

增加v从15到15.001,那么J45.003J\approx45.003J≈45.003

  • dJda=3\frac{dJ}{da}=3​da​​dJ​​=3

增加a从7到7.001,那么v=15.001v=\approx15.001v=≈15.001,J45.003J\approx45.003J≈45.003

这里也涉及到链式法则

1.2.3.3 链式法则

  • dJda=dJdvdvda=31=3\frac{dJ}{da}=\frac{dJ}{dv}\frac{dv}{da}=3*1=3​da​​dJ​​=​dv​​dJ​​​da​​dv​​=3∗1=3

J相对于a增加的量可以理解为J相对于v*v相对于a增加的

接下来计算

  • dJdb=6=dJdududb=32\frac{dJ}{db}=6=\frac{dJ}{du}\frac{du}{db}=3*2​db​​dJ​​=6=​du​​dJ​​​db​​du​​=3∗2

  • dJdc=9=dJdududc=33\frac{dJ}{dc}=9=\frac{dJ}{du}\frac{du}{dc}=3*3​dc​​dJ​​=9=​du​​dJ​​​dc​​du​​=3∗3

1.2.3.4 逻辑回归的梯度下降

逻辑回归的梯度下降过程计算图,首先从前往后的计算图得出如下

  • z=wTx+bz = w^Tx + bz=w​T​​x+b

  • y^=a=σ(z)\hat{y} =a= \sigma(z)​y​^​​=a=σ(z)

  • L(y^,y)=(yloga)(1y)log(1a)L(\hat{y},y) = -(y\log{a})-(1-y)\log(1-a)L(​y​^​​,y)=−(yloga)−(1−y)log(1−a)

那么计算图从前向过程为,假设样本有两个特征

问题:计算出JJJ关于zzz的导数

  • dz=dJdadadz=aydz = \frac{dJ}{da}\frac{da}{dz} = a-ydz=​da​​dJ​​​dz​​da​​=a−y
    • dJda=ya+1y1a\frac{dJ}{da} = -\frac{y}{a} + \frac{1-y}{1-a}​da​​dJ​​=−​a​​y​​+​1−a​​1−y​​
    • dadz=a(1a)\frac{da}{dz} = a(1-a)​dz​​da​​=a(1−a)

所以我们这样可以求出总损失相对于w1,w2,bw_1,w_2,bw​1​​,w​2​​,b参数的某一点导数,从而可以更新参数

  • dJdw1=dJdzdzdw1=dzx1\frac{dJ}{dw_1} = \frac{dJ}{dz}\frac{dz}{dw_1}=dz*x1​dw​1​​​​dJ​​=​dz​​dJ​​​dw​1​​​​dz​​=dz∗x1
  • dJdw2=dJdzdzdw1=dzx2\frac{dJ}{dw_2} = \frac{dJ}{dz}\frac{dz}{dw_1}=dz*x2​dw​2​​​​dJ​​=​dz​​dJ​​​dw​1​​​​dz​​=dz∗x2
  • dJdb=dz\frac{dJ}{db}=dz​db​​dJ​​=dz

相信上面的导数计算应该都能理解了,所以当我们计算损失函数的某个点相对于w1,w2,bw_1,w_2,bw​1​​,w​2​​,b的导数之后,就可以更新这次优化后的结果。

w1:=w1αdJ(w1,b)dw1w_1 := w_1 - \alpha\frac{dJ(w_1, b)}{dw_1}w​1​​:=w​1​​−α​dw​1​​​​dJ(w​1​​,b)​​

w2:=w2αdJ(w2,b)dw2w_2 := w_2 - \alpha\frac{dJ(w_2, b)}{dw_2}w​2​​:=w​2​​−α​dw​2​​​​dJ(w​2​​,b)​​

b:=bαdJ(w,b)dbb := b - \alpha\frac{dJ(w, b)}{db}b:=b−α​db​​dJ(w,b)​​

1.2.4 向量化编程

每更新一次梯度时候,在训练期间我们会拥有m个样本,那么这样每个样本提供进去都可以做一个梯度下降计算。所以我们要去做在所有样本上的计算结果、梯度等操作

J(w,b)=1mi=1mL(a(i),y(i))J(w,b) = \frac{1}{m}\sum_{i=1}mL({a},y^{(i)})J(w,b)=​m​​1​​∑​i=1​m​​L(a​(i)​​,y​(i)​​)

计算参数的梯度为:这样,我们想要得到最终的dw1,dw2,dbd{w_1},d{w_2},d{b}dw​1​​,dw​2​​,db,如何去设计一个算法计算?伪代码实现:

1.2.4.1 向量化优势

什么是向量化

由于在进行计算的时候,最好不要使用for循环去进行计算,因为有Numpy可以进行更加快速的向量化计算。

在公式z=wTx+bz = w^Tx+bz=w​T​​x+b中w,xw,xw,x都可能是多个值,也就是

import numpy as np
import time
a = np.random.rand(100000)
b = np.random.rand(100000)
  • 第一种方法
  
  
# 第一种for 循环
  
  
c = 0
start = time.time()
for i in range(100000):
    c += a[i]*b[i]
end = time.time()

print("计算所用时间%s " % str(1000*(end-start)) + "ms")
  • 第二种向量化方式使用np.dot
  
  
# 向量化运算
  
  
start = time.time()
c = np.dot(a, b)
end = time.time()
print("计算所用时间%s " % str(1000*(end-start)) + "ms")

Numpy能够充分的利用并行化,Numpy当中提供了很多函数使用

函数 作用
np.ones or np.zeros 全为1或者0的矩阵
np.exp 指数计算
np.log 对数计算
np.abs 绝对值计算

所以上述的m个样本的梯度更新过程,就是去除掉for循环。原本这样的计算

1.2.4.2 向量化实现伪代码

  • 思路
z1=wTx1+bz^1 = wTx1+bz​1​​=w​T​​x​1​​+b z2=wTx2+bz^2 = wTx2+bz​2​​=w​T​​x​2​​+b z3=wTx3+bz^3 = wTx3+bz​3​​=w​T​​x​3​​+b
a1=σ(z1)a^1 = \sigma(z^1)a​1​​=σ(z​1​​) a2=σ(z2)a^2 = \sigma(z^2)a​2​​=σ(z​2​​) a3=σ(z3)a^3 = \sigma(z^3)a​3​​=σ(z​3​​)

可以变成这样的计算

注:w的形状为(n,1), x的形状为(n, m),其中n为特征数量,m为样本数量

我们可以让,得出的结果为(1, m)大小的矩阵 注:大写的wx为多个样本表示

  • 实现多个样本向量化计算的伪代码

这相当于一次使用了M个样本的所有特征值与目标值,那我们知道如果想多次迭代,使得这M个样本重复若干次计算

1.2.5 案例:实现逻辑回归

1.2.5.1使用数据:制作二分类数据集

from sklearn.datasets import load_iris, make_classification
from sklearn.model_selection import train_test_split
import tensorflow as tf
import numpy as np

X, Y = make_classification(n_samples=500, n_features=5, n_classes=2)
x_train, x_test, y_train, y_test = train_test_split(X, Y, test_size=0.3)

1.2.5.2 步骤设计:

分别构建算法的不同模块

  • 1、初始化参数
def initialize_with_zeros(shape):
    """
    创建一个形状为 (shape, 1) 的w参数和b=0.
    return:w, b
    """

    w = np.zeros((shape, 1))
    b = 0

    return w, b
  • 计算成本函数及其梯度

    • w (n,1).T * x (n, m)
    • y: (1, n)
def propagate(w, b, X, Y):
    """
    参数:w,b,X,Y:网络参数和数据
    Return:
    损失cost、参数W的梯度dw、参数b的梯度db
    """
    m = X.shape[1]

    # w (n,1), x (n, m)
    A = basic_sigmoid(np.dot(w.T, X) + b)
    # 计算损失
    cost = -1 / m * np.sum(Y * np.log(A) + (1 - Y) * np.log(1 - A))
    dz = A - Y
    dw = 1 / m * np.dot(X, dz.T)
    db = 1 / m * np.sum(dz)

    cost = np.squeeze(cost)

    grads = {"dw": dw,
             "db": db}

    return grads, cost

需要一个基础函数sigmoid

def basic_sigmoid(x):
    """
    计算sigmoid函数
    """

    s = 1 / (1 + np.exp(-x))

    return s
  • 使用优化算法(梯度下降)

    • 实现优化函数. 全局的参数随着w,b对损失J进行优化改变. 对参数进行梯度下降公式计算,指定学习率和步长。

    • 循环:

      • 计算当前损失
      • 计算当前梯度
      • 更新参数(梯度下降)
def optimize(w, b, X, Y, num_iterations, learning_rate):
    """
    参数:
    w:权重,b:偏置,X特征,Y目标值,num_iterations总迭代次数,learning_rate学习率
    Returns:
    params:更新后的参数字典
    grads:梯度
    costs:损失结果
    """

    costs = []

    for i in range(num_iterations):

        # 梯度更新计算函数
        grads, cost = propagate(w, b, X, Y)

        # 取出两个部分参数的梯度
        dw = grads['dw']
        db = grads['db']

        # 按照梯度下降公式去计算
        w = w - learning_rate * dw
        b = b - learning_rate * db

        if i % 100 == 0:
            costs.append(cost)
        if i % 100 == 0:
            print("损失结果 %i: %f" %(i, cost))
            print(b)

    params = {"w": w,
              "b": b}

    grads = {"dw": dw,
             "db": db}

    return params, grads, costs
  • 预测函数(不用实现)

利用得出的参数来进行测试得出准确率

def predict(w, b, X):
    '''
    利用训练好的参数预测
    return:预测结果
    '''

    m = X.shape[1]
    y_prediction = np.zeros((1, m))
    w = w.reshape(X.shape[0], 1)

    # 计算结果
    A = basic_sigmoid(np.dot(w.T, X) + b)

    for i in range(A.shape[1]):

        if A[0, i] <= 0.5:
            y_prediction[0, i] = 0
        else:
            y_prediction[0, i] = 1

    return y_prediction
  • 整体逻辑

    • 模型训练
def model(x_train, y_train, x_test, y_test, num_iterations=2000, learning_rate=0.0001):
    """
    """

    # 修改数据形状
    x_train = x_train.reshape(-1, x_train.shape[0])
    x_test = x_test.reshape(-1, x_test.shape[0])
    y_train = y_train.reshape(1, y_train.shape[0])
    y_test = y_test.reshape(1, y_test.shape[0])
    print(x_train.shape)
    print(x_test.shape)
    print(y_train.shape)
    print(y_test.shape)

    # 1、初始化参数
    w, b = initialize_with_zeros(x_train.shape[0])

    # 2、梯度下降
    # params:更新后的网络参数
    # grads:最后一次梯度
    # costs:每次更新的损失列表
    params, grads, costs = optimize(w, b, x_train, y_train, num_iterations, learning_rate)

    # 获取训练的参数
    # 预测结果
    w = params['w']
    b = params['b']
    y_prediction_train = predict(w, b, x_train)
    y_prediction_test = predict(w, b, x_test)

    # 打印准确率
    print("训练集准确率: {} ".format(100 - np.mean(np.abs(y_prediction_train - y_train)) * 100))
    print("测试集准确率: {} ".format(100 - np.mean(np.abs(y_prediction_test - y_test)) * 100))

    return None
  • 训练
model(x_train, y_train, x_test, y_test, num_iterations=2000, learning_rate=0.0001)

未完待续, 同学们请等待下一期

完整笔记代码请移步:

请移步这里获取文档和代码

感兴趣的小伙伴可以自取哦,欢迎大家点赞转发~

标签:dz,md,frac,train,文档,Logistic,dw,np,dJ
From: https://www.cnblogs.com/yinuo112/p/18031778

相关文章

  • SharePoint Online 启用文档库多行文本的富文本属性
    前言相信大家都知道我们可以在列表中快速创建支持富文本的多行文本字段,但是,文档库中不行。正文1.这是列表中的多行文本字段,可以点击编辑图标,如下图:2.然后,会弹出一个富文本编辑框,支持富文本,如下图:3.但是,在文档库中新建多行文本的时候,少了一些属性,如......
  • kkFileView文档在线预览项目在IDEA运行正常正常,打包jar提示找不到office组件,请确认'of
    2024-02-2413:36:58.530WARN17976---[main]ConfigServletWebServerApplicationContext:Exceptionencounteredduringcontextinitialization-cancellingrefreshattempt:org.springframework.beans.factory.BeanCreationException:Errorcreatingbeanwithn......
  • MD5加密工具类
     介绍:一个简单的MD5加密工具类,用于对字符串进行MD5加密。 /***@description:MD5加密工具类*/publicclassMD5Util{//将字节数组转换为对应的十六进制字符串。privatestaticStringbyteArrayToHexString(byteb[]){StringBufferresultSb=......
  • MDS500-16-ASEMI工业电机专用MDST150-16
    编辑:llMDS500-16-ASEMI工业电机专用MDST150-16型号:MDS500-16品牌:ASEMI正向电流(Id):500A反向耐压(VRRM):1600V正向浪涌电流:600A正向电压(VF):1.38V引脚数量:5芯片个数:6芯片尺寸:MIL功率(Pd):大功率设备封装:M34工作温度:-40°C~125°C类型:整流模块、整流桥MDS500-16描述:ASEMI品......
  • MDS300-16-ASEMI电源控制柜MDS300-16
    编辑:llMDS300-16-ASEMI电源控制柜MDS300-16型号:MDS300-16品牌:ASEMI封装:M25最大重复峰值反向电压:1600V最大正向平均整流电流(Vdss):300A功率(Pd):大功率芯片个数:6引脚数量:5类型:整流模块、整流桥正向浪涌电流:600A正向电压:1.35V最大输出电压(RMS):封装尺寸:如图工作温度:-40......
  • FirstMD
    如何遍历一个窗体中的某一种控件假设我要遍历所有的Label控件.我们知道一个窗体中的所有控件都是Form.Controls中的成员,想要得到窗体中的所以成员,可以用foreach来遍历Controls属性中的对象。注意,Controls属性中包含的对象都是以Control基类形式存在的,这就是说我们只能用foreach......
  • AMD GI-1.0 Screen Probe改进分析
    目录ScreenProbeReuse(GI-1.0)AMDScreenProbe生成(SpawnScreenProbe)重投影(ReprojectionScreenProbe)重投影的优化交换队列自适应补洞LRU存储多帧HistoryProbe采样(RaySampling)1/4需要重新生成的ProbeReprojection失败生成ProbeReprojection成功生成Probe3/4不需要重新生成的P......
  • 安全运维:cmd命令大全(108个)
    1、calc:启动计算器2、appwiz.cpl:程序和功能3、certmgr.msc:证书管理实用程序4、charmap:启动字符映射表5、chkdsk.exe:Chkdsk磁盘检查(管理员身份运行命令提示符)6、cleanmgr:打开磁盘清理工具7、cliconfg:SQLSERVER客户端网络实用工具8、cmstp:连接管理器配置文件安装程序9......
  • 删除Windows 11 文件资源管理器 左侧的图标(最全) 文档、音乐、视频、图片、图库、主
    删除Windows11文件资源管理器左侧的图标(最全)文档、音乐、视频、图片、图库、主文件夹等1、删除此电脑(文件资源管理器)左侧的图标,文件夹下的全部文件夹都可以删除,推荐重命名一下跟之前不一样就好了,删除此电脑(文件资源管理器)左侧的图标,文件夹下的全部文件夹都可以删除,推......
  • MDST150-16-ASEMI三相可控整流模块MDST150-16
    编辑:llMDST150-16-ASEMI三相可控整流模块MDST150-16型号:MDST150-16品牌:ASEMI正向电流(Id):150A反向耐压(VRRM):1600V正向浪涌电流:1200A正向电压(VF):1.30V引脚数量:5芯片个数:6芯片尺寸:MIL功率(Pd):大功率设备封装:M18工作温度:-55°C~150°C类型:整流模块、整流桥MDST150-16描述......