【机器学习】P17 梯度下降 与 梯度下降优化算法(BGD 等 与 Adam Optimizer、AdaGrad、RMSProp)

news2024/11/25 0:33:48

梯度下降与梯度下降算法

  • 梯度下降
  • 梯度下降算法
    • 基础优化算法
      • 批量梯度下降 BGD
      • 随机梯度下降 SGD
      • 小批量梯度下降 MBGD
      • 动量梯度下降 MGD
    • 基础优化算法上的改进和优化的算法
      • 自适应梯度算法 Adagrad
      • 均方根传播算法 RMSProp
      • 自适应矩估计算法 Adam
  • 代码如何实现梯度下降
  • 如何判断收敛

梯度下降

梯度下降(Gradient Descent)是一种常用的优化算法,用于求解目标函数的最小值。(在机器学习应用梯度下降中,主要目标是为了最小化损失函数);

其基本思想是通过不断迭代调整参数,使得目标函数的值不断逼近最小值。(机器学习中是为了最小化损失函数,即使得预测值与实际值之间的差值最小);

在每一次迭代中,算法会计算当前参数的梯度值,然后将参数朝着梯度下降的方向进行更新,从而达到逐步降低目标函数值的目的。

总而言之,梯度下降之于机器学习:

  • 目标和意义:
    梯度下降算法的目标是最小化损失函数,通过计算损失函数对权重的偏导数(即梯度)来确定更新权重的方向和大小。

  • 基本公式:
    θ i + 1 = θ i − α ∂ J ( θ ) ∂ θ \theta_{i+1} = \theta _i - \alpha \frac {\partial J(\theta)} {\partial \theta} θi+1=θiαθJ(θ)

  • 学习率:
    学习率决定了每次迭代中,参数更新的幅度,如果学习率设置得过大,可能会导致参数不断在损失函数的最小值两侧来回震荡,无法收敛;而如果学习率设置得过小,可能会导致参数更新速度过慢,收敛速度变慢。
    因此,合适的学习率对梯度下降算法的收敛速度和效果至关重要。


梯度下降算法

梯度下降算法,我分为两个派系共计7个算法:

  • 基础优化算法:
    批量梯度下降 BGD 随机梯度下降 SGD 小批量梯度下降 MBGD 动量梯度下降 MGD
  • 基础优化算法上改进和优化的算法:
    自适应梯度算法 Adagrad 均方根传播算法 RMSProp 自适应矩估计算法 Adam

省流来说,无脑用 Adam 就行;剩余分析内容如下

基础优化算法

批量梯度下降 BGD

批量梯度下降算法 Batch Gradient Descent,在每次迭代时使用全部的训练数据来计算梯度,然后用这个梯度更新模型参数。因此,BGD 的运行时间与训练数据的大小成正比,当数据集很大时,它的运行时间会很长。

具体来说,BGD 的流程如下:

  1. 初始化模型参数,例如随机赋值。
  2. 计算训练数据集的损失函数。
  3. 计算损失函数的梯度,即对所有样本的梯度进行求和并求平均值,注意是所有训练样本。
  4. 使用梯度下降的公式来更新模型参数,使得损失函数减小。
  5. 重复 2~4 步,直到损失函数达到满意的值或达到最大迭代次数。

批量梯度下降 Batch Gradient Descent 的优点是可以全局优化模型,有效的避免局部最优解的出现,但是无法完全规避局部最优解;但相比于其他优化算法,它的局部最优解问题较少。同时,BGD 收敛速度相对较快。

缺点是需要遍历整个训练集,计算梯度的时间较长,不适合大规模数据集的训练。另外,BGD 对于数据集中存在噪声或异常值的情况比较敏感,需要进行数据预处理或采用其他优化算法。


随机梯度下降 SGD

随机梯度下降算法 Stochastic Gradient Descent 与批量梯度下降算法不同的是,它不是计算所有样本的梯度来更新模型参数,而是从训练集中随机选择一个样本计算梯度,并使用该样本梯度来更新参数。

带着疑惑,SGD 的流程如下:

  1. 初始化模型参数,通常为随机值。
  2. 随机从训练集中选择一个样本。
  3. 计算该样本的损失函数在当前模型参数处的梯度。
  4. 使用计算出的梯度来更新模型参数。
  5. 重复步骤2-4,直到达到预设的停止条件。

很明显,SGD每次只需要计算一个样本的梯度,所以计算速度快,适合大规模数据集。

更明显,由于随机性的存在,可能导致每次更新参数的方向不一样,可能会导致算法在训练过程中出现震荡现象,需要增加一些技巧来解决这个问题。

在SGD的基础上,还有一些改进的算法,如批量随机梯度下降(Mini-Batch SGD)和动量梯度下降(Momentum),它们可以更好地平衡计算速度和算法稳定性,使得训练过程更加高效和可靠。


小批量梯度下降 MBGD

小批量梯度下降算法,Mini-Batch Gradient Descent,在每次迭代时仅使用部分数据(即一个小批量)来计算梯度,从而减少计算量,加快收敛速度,同时也能提高收敛的稳定性。

带着灵光乍现,MBGD 的流程如下:

  1. 随机选择一个大小为 m 的小批量数据,其中 m 通常是 2 的整数次幂,可以根据实际情况进行调整。
  2. 计算这个小批量数据的平均梯度。
  3. 根据计算出的平均梯度更新模型参数,即执行参数更新公式:θ = θ - α * g,其中θ表示模型参数,α表示学习率,g表示平均梯度。
  4. 重复步骤1-3,直到达到收敛条件或达到预设的迭代次数。

很明显,MBGD 是 BGD 与 SGD 的一种折中算法,包含两个的优势。算的快,收敛的快,更稳定;


动量梯度下降 MGD

动量梯度下降,Momentum Gradient Descent,在更新参数时,除了考虑当前的梯度,还要考虑之前梯度的方向和大小。具体来说,MGD引入了一个动量变量,用来记录之前的梯度方向,然后将当前梯度方向和动量方向结合起来进行参数更新。

带着些许点头,MGD 的流程如下:

  1. 初始化动量变量v为0。
  2. 计算当前的梯度g。
  3. 更新动量变量v:v = βv + (1-β)g,其中β是一个介于0和1之间的动量系数。
  4. 根据动量变量v和当前梯度g的和来更新模型参数:θ = θ - α(v+g),其中α是学习率。
  5. 重复执行2-4步,直到达到收敛条件或达到预设的迭代次数。

感觉上,好像动量梯度下降在小批量梯度下降上做了一些优化,即加上了一个参数——动量变量,但是真的有很好的优化效果吗?

但是事实上不一定,并不是说只要选择合适的动量变量v,MGD 就一定优于 MBGD;
优化算法的选择,需要考虑很多因素的影响,比如数据集大小、模型复杂度、超参数设置等等。对于不同的问题,可能需要不同的优化算法才能获得最好的效果。

同时,MGD 中选择动量变量 v 的大小也是需要进行调整的,如果设置得不合适,也可能导致收敛速度变慢或不稳定的收敛。


基础优化算法上的改进和优化的算法

自适应梯度算法 Adagrad

Adagrad在每个参数处维护一个二次累积梯度的平方和,用于根据参数的历史梯度信息自适应地调整学习率。每次迭代时,Adagrad根据当前参数的梯度计算其二次累积梯度的平方和,并使用该平方和来更新参数的学习率。

带着什么是“二次累积梯度”的疑问,Adagrad 更新参数的公式如下:
θ t + 1 , i = θ t , i − α G t , i i + ϵ g t , i \theta_{t+1, i} = \theta_{t,i} - \frac {\alpha} {\sqrt{G_{t,ii} + \epsilon}}g_{t,i} θt+1,i=θt,iGt,ii+ϵ αgt,i

其中 θ t + 1 , i \theta_{t+1, i} θt+1,i 为第 i i i 个参数在 t + 1 t+1 t+1 时刻,即更新后的取值;
对应的 θ t , i \theta_{t, i} θt,i 即为第 i i i 个参数在 t t t 时刻,即更新前的取值;
α \alpha α 学习率;
g t , i g_{t,i} gt,i 该参数在 t t t 时刻的梯度;
G t , i i G_{t,ii} Gt,ii 是参数在 t t t 时刻的二次累积梯度平方和;
ϵ \epsilon ϵ 是一个非常小的常数,用于规避分母为 0 的情况;

  • 什么是二次累积梯度平方和?
    二次累积梯度平方和,也称为 历史梯度平方和,用来自适应地调整参数的学习率。具体地,假设在前 t t t 个时刻中,第 i i i 个参数 θ i \theta_i θi 的梯度为 g 1 , i , g 2 , i , … , g t , i g_{1,i}, g_{2,i}, \dots, g_{t,i} g1,i,g2,i,,gt,i,那么它在第 t t t 个时刻的二次累积梯度平方和为:
    G t , i i = ∑ k = 1 t ( g k , i ) 2 G_{t,ii} = \sum _{k=1} ^{t} (g_{k,i})^2 Gt,ii=k=1t(gk,i)2
    具体来说,Adagrad算法中,二次累积梯度平方和 G t , i i G_{t,ii} Gt,ii 可以被看做是每个参数 θ i \theta_i θi 的历史梯度信息的加权平均,其中较大的梯度会获得较小的权重,较小的梯度会获得较大的权重,从而达到自适应调整学习率的目的。

根据 Adagrad 更新参数的公式:
θ t + 1 , i = θ t , i − α G t , i i + ϵ g t , i \theta_{t+1, i} = \theta_{t,i} - \frac {\alpha} {\sqrt{G_{t,ii} + \epsilon}}g_{t,i} θt+1,i=θt,iGt,ii+ϵ αgt,i

我们发现 二次累计梯度平方和 出现在:
α G t , i i + ϵ \frac {\alpha} {\sqrt{G_{t,ii} + \epsilon}} Gt,ii+ϵ α

其中, ϵ \epsilon ϵ 是一个非常小的常数,意义就是为了防止分母部分为0,而如果某个参数 θ i \theta_i θi 在之前的迭代中 梯度 g t , i g_{t,i} gt,i 比较大,那么对应的 二次累积梯度平方和 G_{t,ii} 就比较大,因此在后续的迭代中,该参数的学习率部分 α G t , i i + ϵ \frac {\alpha} {\sqrt{G_{t,ii} + \epsilon}} Gt,ii+ϵ α 会减小,使得它在参数空间中移动的步长变小,从而更加稳定地接近最优点。反之,如果某个参数在之前的迭代中梯度比较小,那么对应的二次累积梯度平方和就比较小,因此在后续的迭代中,该参数的学习率会增大,使得它在参数空间中移动的步长变大,从而更快地接近最优点。

因此,Adagrad算法使用二次累积梯度平方和来调整每个参数的学习率,能够自适应地为不同的参数分配不同的学习率,从而更加有效地优化模型。


均方根传播算法 RMSProp

与Adagrad算法类似,RMSProp算法也使用了梯度的二次累积信息,但是与Adagrad算法不同的是,RMSProp算法对梯度的二次累积信息进行了指数加权移动平均(Exponential Moving Average,EMA),而不是简单的累加和

具体来说,对于某个参数 w w w 的梯度 g t g_t gt,RMSProp算法使用如下的指数加权移动平均公式计算它的二次累积梯度平方和:
v t = β v t − 1 + ( 1 − β ) g t 2 v_t = \beta v_{t-1} + (1-\beta) g_t^2 vt=βvt1+(1β)gt2

其中, v t v_t vt 表示第 t t t 是迭代时参数 w w w 的二次累积梯度平方和, β \beta β 是一个介于0~1 之间的衰减率,用来控制历史梯度信息的权重大小,通常取值 0.9 或 0.99;

剩下的部分同 Adagrad,即 RMSProp 的更新参数的公式为:
θ t + 1 , i = θ t , i − α v t + ϵ g t , i \theta_{t+1, i} = \theta_{t,i} - \frac {\alpha} {\sqrt{v_t + \epsilon}}g_{t,i} θt+1,i=θt,ivt+ϵ αgt,i

RMSProp算法根据每个参数的历史梯度信息来自适应地调整学习率,如果某个参数的梯度比较大,那么它的二次累积梯度平方和也会比较大,此时它的学习率会减小,使得它在参数空间中移动的步长变小,从而更加稳定地接近最优点。

反之,如果某个参数的梯度比较小,那么它的二次累积梯度平方和也会比较小,此时它的学习率会增大,使得它在参数空间中移动的步长变大,从而更快地接近最优点。

总的来说,RMSProp算法相比于传统的梯度下降算法,能够自适应地调整每个参数的学习率,从而更加高效地优化模型。


对比 Adagrad 与 RMSProp 来看,

RMSProp只考虑最近一段时间的历史梯度平方和,而不是所有历史的平方和(Adagrad),所以它可以更快地适应梯度的变化,并且可以处理非凸优化问题中的局部极小值。

可以认为RMSProp可以缓解Adagrad中因为一开始参数非常大而后来比较小,但是值一直比较大所以 α \alpha α 一直很大,导致下降快的问题。

在实际应用中,我们需要根据具体情况选择适合的梯度优化算法。例如,在处理稀疏数据时,Adagrad可能更适合;而在处理非凸优化问题时,RMSProp可能更适合。


自适应矩估计算法 Adam

Adam是非常常用的自适应优化算法,可以自适应地调整每个参数的学习率,并具有一些正则化的特性。是 Adagrad 和 RMSProp 的扩展版本,同时具备 Adagrad 和 RMSProp 的优点,同时引入了动量的概念。

具体来说,Adam算法通过以下步骤进行参数更新:

  1. 计算梯度的一阶矩估计(均值)和二阶矩估计(方差),分别表示为 m m m v v v,它们分别初始化为 0。
  2. 计算梯度 g t g_t gt
  3. 计算当前梯度的一阶矩估计 m m m 和二阶矩估计 v v v 的加权平均值,分别表示为 m_hat 和 v_hat。具体来说,对于每个参数 θ i θ_i θi,它们的更新方式为:
    m = β 1 ∗ m + ( 1 − β 1 ) ∗ g t v = β 2 ∗ v + ( 1 − β 2 ) ∗ g t 2 m = \beta_1 * m + (1-\beta_1) * g_t \\ v = \beta_2 * v + (1-\beta_2) * g_t ^2 m=β1m+(1β1)gtv=β2v+(1β2)gt2

超参数 β 1 \beta_1 β1 β 2 \beta_2 β2

在Adam算法中,超参数β1和β2分别控制一阶矩和二阶矩的指数衰减率,它们的作用是平衡历史梯度信息和当前梯度信息对参数更新的影响。

具体来说,β1控制历史梯度信息的衰减速度,它通常取0.9。这意味着当前的梯度在计算一阶矩估计时所占的权重为0.1,历史梯度在计算一阶矩估计时所占的权重为0.9,因此一阶矩估计可以平滑历史梯度信息,使得参数更新更加稳定。

β2控制二阶矩估计的衰减速度,它通常取0.999。这意味着当前的梯度平方在计算二阶矩估计时所占的权重为0.001,历史梯度平方在计算二阶矩估计时所占的权重为0.999,因此二阶矩估计可以平滑历史梯度平方信息,使得参数更新更加稳定。

调整β1和β2的值可以对Adam算法的性能产生重要影响。通常情况下,β1和β2的值是不需要进行调整的,因为它们已经在大量实验中被证明是比较合适的取值。但是,在一些特殊的任务中,可能需要根据具体情况来调整β1和β2的值,以达到更好的优化效果。


接上述公式步骤部分:

  1. 矫正偏差:在Adam算法中,由于一阶矩和二阶矩的初始估计值都是0,因此在算法的初期阶段,这些估计值会受到偏差影响,导致算法表现不佳。为了解决这个问题,Adam算法引入了偏差校正机制。
    偏差校正通过在计算一阶矩和二阶矩估计值时,除以一个偏差校正因子来进行校正。这个偏差校正因子是由当前的迭代次数t和指数衰减率β1、β2共同决定的。
    通过偏差校正,可以减轻一阶矩和二阶矩估计值受到初始值偏差的影响,从而提高算法的表现。特别是在算法的初期阶段,偏差校正的效果更加显著,可以使算法更快地收敛。
    总之,偏差校正是Adam算法中非常重要的一部分,它可以减轻算法受到初始值偏差的影响,提高算法的表现。
    m h a t = m / ( 1 − β 1 t ) v h a t = v / ( 1 − β 2 t ) m_{hat} = m / (1-\beta_1^t)\\ v_{hat} = v / (1-\beta_2^t) mhat=m/(1β1t)vhat=v/(1β2t)

  2. 更新参数:
    θ = θ − α v h a t + ϵ m h a t \theta = \theta - \frac {\alpha} {\sqrt {v_{hat}} + \epsilon}m_{hat} θ=θvhat +ϵαmhat

其中, m h a t m_{hat} mhat 为动量估计量,包含 gradient 信息,而 v h a t v_{hat} vhat 则为RMSProp 梯度的指数加权平均值,当梯度变化剧烈时,v 的值会变得较大,导致更新步长较小;而当梯度变化较小时,v 的值会变得较小,导致更新步长较大。这样就能够平衡梯度的变化和更新步长,从而更好地优化模型。

在训练神经网络时,Adam Optimizer通常是一种非常实用的优化算法,因为它能够自适应地调整每个权重的学习率,从而更快地收敛,并且在超参数设置上相对简单。


所以,回头来看,基础优化算法,其实是在梯度下降的训练数据集规模上做选择,是全部训练数据集(BGD),还是就一个训练数据(SGD),还是一部分训练数据(MBGD);而基础优化算法的改进上,都是围绕如何合理动态规划学习率 α \alpha α 来控制下降的快慢。


代码如何实现梯度下降

Tensorflow 举例 Adam Gradient Descent:

在这里插入图片描述
Adam 自适应矩估计算法,通过对每个参数的学习率进行控制;在tensorflow中代码实现如下:

import tensorflow as tf

model.compile(optimizer=tf.keras.optimizers.Adam(learning_rate=1e-3))

如何判断收敛

几种常见的判断模型是否收敛的方法:

  1. 损失函数下降: 在训练过程中,损失函数会逐渐下降,如果损失函数已经下降到一定程度而不再变化,可以判定模型已经收敛。

  2. 参数变化: 模型的参数在训练过程中会发生变化,如果模型的参数值已经趋于稳定,说明模型已经收敛。

  3. 梯度变化: 梯度代表了损失函数的变化趋势,如果梯度变化已经趋于平缓,说明模型已经收敛。

  4. 验证集误差: 在训练过程中,可以使用验证集验证模型的泛化性能,如果验证集误差已经趋于稳定,说明模型已经收敛。

综上所述,无法收敛不仅仅是准确率不能提高,还有可能是损失函数不下降、参数变化过大、梯度变化过大、验证集误差波动等情况。因此,在实际应用中,需要综合考虑多种指标来判断模型是否收敛。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/417807.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

pytorch搭建ResNet50实现鸟类识别

🍨 本文为🔗365天深度学习训练营 中的学习记录博客 🍦 参考文章地址: 365天深度学习训练营-第J1周:ResNet-50算法实战与解析 🍖 作者:K同学啊 理论知识储备 深度残差网络ResNet(dee…

KD2511N高精度直流低电阻值测试仪

一、产品简介 KD2511N直流低电阻测试仪采用32bits CPU和高密度 SMD贴装工艺, 拥有0.05%的 电阻测量精度及1uΩ 小电阻分辨率,内部比较器可让使用者自行设定上限/下限参考比较值。高达每秒15次的测试速度能显著提高工作效率,免清零的设计在小电…

数据结构刷题笔记 | 数组、字符串、链表、栈、队列、数、图

本篇为笔者学习数据结构时,在牛客网站的刷题笔记。 数据结构分为: 逻辑结构【面向问题的】 集合结构线性结构(一对一)树形结构(一对多的层次关系)图形结构(多对多) 物理结构&#x…

Docker 实战笔记-基础

转载请标明出处:http://blog.csdn.net/zhaoyanjun6/article/details/130181636 本文出自【赵彦军的博客】 文章目录官网下载安装安装Docker 镜像常用命令docker infodocker imagesdocker versiondocker 仓库官方仓库:[https://hub.docker.com/](https://…

移动端树形结构

该组件依据需求来做,当前包含三种选择状态,选中,未选中,半选。由于不需要做树形的收缩展开故没有写相关内容。树形展开与收缩与选中类似,只需要在节点上挂载相关字段即可实现。由于需求需要增加不限的功能,…

Moonbeam操作指南 | 如何设置Moonbeam开发节点

Moonbeam开发节点是为本地构建和测试应用的个人开发环境。对以太坊开发者来说,可以和Ganache相媲美。可以使你快速上手,且无需中继链的支出即可轻松实现。 有2种方式可以开始运行节点:使用Docker运行一个预构建的二进制文件,或者…

Java面试宝典

JDK,JRE,JVM 三者关系? JDK 是 JAVA 程序开发时用的开发工具包,其内部也有 JRE 运行环境 JRE。JRE 是 JAVA 程序运行时需要的运行环境,就是说如果你光是运行 JAVA 程序而不是去搞开发的话,只安装 JRE 就能运行已经存在的 JAVA 程…

我们发送的信息数据是怎么处理的?

下图以用户 a 向用户 b 发送邮件为例子: 数据处理流程 1、应用程序处理 首先应用程序会进行编码处理,这些编码相当于 OSI 的表示层功能; 编码转化后,邮件不一定马上被发送出去,这种何时建立通信连接何时发送数据的管…

5G/V2X赛道「重启」

在提升高阶智能驾驶安全性和感知冗余能力的道路上,除了激光雷达、高精度地图及定位,还有一项技术可能即将掀起一场新的风暴。 就在今年3月,作为全球通信领域的年度风向标 — 2023世界移动通信大会(MWC)上,…

无需魔法打开即用的 AI 工具集锦

作者:明明如月学长, CSDN 博客专家,蚂蚁集团高级 Java 工程师,《性能优化方法论》作者、《解锁大厂思维:剖析《阿里巴巴Java开发手册》》、《再学经典:《EffectiveJava》独家解析》专栏作者。 热门文章推荐…

Tomcat源码:StandardEngine、StandardHost、StandardContext、StandardWrapper

前文: 《Tomcat源码:启动类Bootstrap与Catalina的加载》 《Tomcat源码:容器的生命周期管理与事件监听》 《Tomcat源码:StandardServer与StandardService》 《Tomcat源码:Container接口》 写在开头:本文…

【C++STL精讲】vector的模拟实现

文章目录💐专栏导读💐文章导读🌷定义vector类🌷各成员函数的实现🌺构造函数🌺迭代器🌺size与capacity——求大小与容量🌺reserve——扩容关于reserve中的深浅拷贝问题🌺r…

RK3399平台开发系列讲解(基础篇)ADC 使用方法

🚀返回专栏总目录 文章目录 一、ADC 的 DTS 配置二、ADC 驱动说明2.1、获取 AD 通道2.2、读取 AD 采集到的原始数据2.3、计算采集到的电压三、接口说明沉淀、分享、成长,让自己和他人都能有所收获!😄 📢内核采用工业 I/O 子系统来控制 ADC,该子系统主要为 AD 转换或者…

Day920.结构化日志业务审计日志 -SpringBoot与K8s云原生微服务实践

结构化日志&业务审计日志 Hi,我是阿昌,今天学习记录的是关于结构化日志&业务审计日志的内容。 1、什么是结构化日志 结构化日志(Structured Logging)是一种将日志信息组织为结构化数据的技术。 传统的日志通常是一些文…

浏览器前进与后退的秘密——栈 (栈的理解与实现)

文章目录前言:浏览器与栈的纠缠如何理解“栈”?如何实现一个“栈”?基于数组的顺序栈基于链表的链式栈解答开篇🐱‍🐉作者简介:大家好,我是黑洞晓威,一名大二学生,希望和…

0010_C++语言_简单的C++程序

系列文章目录 0001_C语言_C入门 文章目录 系列文章目录 前言 一、写一个简单的C程序 二、来看看这个程序 1.返回类型 2.函数名 3.形参列表 4.函数体 总结 前言 期中考试完毕!(在此祝宫野艾莲娜小姐考得很好!) 今天来看一个简单…

AXI write data在Write data channel的排布

前几天帮一位同事分析了下write data在AXI write data channel上排布,想想还是记录一下,方便日后复习。我们先来看一张wdata排布图,灰色单元表示该Byte没有被传输。 第一次看这张图的时候,是否有感觉疑惑: address为0…

Mysql-锁机制

Mysql的锁机制 一、简介 锁是为了保证数据库中数据的一致性,使各种【共享资源】在被访问时变得【有序】而设计的一种规则。 tip MysQL中不同的存储引擎支持不同的锁机制: InoDB支持【行锁】,有时也会升级为表锁。MyIsam只支持表锁。 【表锁…

实验6 TensorFlow基础

1. 实验目的 掌握TensorFlow低阶API,能够运用TensorFlow处理数据以及对数据进行运算。 2.实验内容 ①实现张量维度变换,部分采样等; ②实现张量加减乘除、幂指对数运算; ③利用TensorFlow对数据集进行处理。 3.实验过程 题目…

UE4 几种常见的项目优化方式

1.灯光范围优化 当屏幕某一块像素被多盏灯光所影响,那么也会拖慢帧率,可以打开灯光复杂度视图进行查看,屏幕上越红的地方灯光复杂度越高,尝试降低灯光半径可以解决: 2.材质纹素优化 有时候我们并不知道目标模型的…