pytorch tensor查找0_扩展之Tensorflow2.0 | 20 TF2的eager模式与求导

【机器学习炼丹术】的学习笔记分享 <>

扩展之Tensorflow2.0 | 19 TF2模型的存储与载入

扩展之Tensorflow2.0 | 18 TF2构建自定义模型

扩展之Tensorflow2.0 | 17 TFrec文件的创建与读取

扩展之Tensorflow2.0 | 16 TF2读取图片的方法

扩展之Tensorflow2.0 | 15 TF2实现一个简单的服装分类任务

小白学PyTorch | 14 tensorboardX可视化教程

小白学PyTorch | 13 EfficientNet详解及PyTorch实现

小白学PyTorch | 12 SENet详解及PyTorch实现

小白学PyTorch | 11 MobileNet详解及PyTorch实现

小白学PyTorch | 10 pytorch常见运算详解

小白学PyTorch | 9 tensor数据结构与存储结构

小白学PyTorch | 8 实战之MNIST小试牛刀

小白学PyTorch | 7 最新版本torchvision.transforms常用API翻译与讲解

小白学PyTorch | 6 模型的构建访问遍历存储(附代码)

小白学PyTorch | 5 torchvision预训练模型与数据集全览

小白学PyTorch | 4 构建模型三要素与权重初始化

小白学PyTorch | 3 浅谈Dataset和Dataloader

小白学PyTorch | 2 浅谈训练集验证集和测试集

小白学PyTorch | 1 搭建一个超简单的网络

小白学PyTorch | 动态图与静态图的浅显理解

这个系列《小白学PyTorch》的所有代码和数据集放在了公众号【机器学习炼丹术】后台,回复【pytorch】获取(还在更新的呢):

f088680af25bc0338e6e6a87013cc73c.png

【新闻】:机器学习炼丹术的粉丝的人工智能交流群已经建立,目前有目标检测、医学图像、时间序列等多个目标为技术学习的分群和水群唠嗑的总群,欢迎大家加炼丹兄为好友,加入炼丹协会。微信:cyx645016617.

c84b32d4366bae2129f8d7bce45a8c40.png

参考目录:

  • 1 什么是eager模式

  • 2 TF1.0 vs TF2.0

  • 3 获取导数/梯度

  • 4 获取高阶导数

之前讲解了如何构建数据集,如何创建TFREC文件,如何构建模型,如何存储模型。这一篇文章主要讲解,TF2中提出的一个eager模式,这个模式大大简化了TF的复杂程度。

1 什么是eager模式

Eager模式(积极模式),我认为是TensorFlow2.0最大的更新,没有之一。

Tensorflow1.0的时候还是静态计算图,在《小白学PyTorch》系列的第一篇内容,就讲解了Tensorflow的静态特征图和PyTorch的动态特征图的区别。Tensorflow2.0提出了eager模式,在这个模式下,也支持了动态特征图的构建

不得不说,改的和PyTorch越来越像了,但是人类的工具总是向着简单易用的方向发展,这肯定是无可厚非的。

2 TF1.0 vs TF2.0

TF1.0中加入要计算梯度,是只能构建静态计算图的。

  1. 是先构建计算流程;
  2. 然后开始起一个会话对象;
  3. 把数据放到这个静态的数据图中。

整个流程非常的繁琐。

# 这个是tensorflow1.0的代码
import tensorflow as tf
a = tf.constant(3.0)
b = tf.placeholder(dtype = tf.float32)
c = tf.add(a,b)
sess = tf.Session() #创建会话对象
init = tf.global_variables_ini                            tializer()
sess.run(init) #初始化会话对象
feed = {
    b: 2.0
} #对变量b赋值
c_res = sess.run(c, feed) #通过会话驱动计算图获取计算结果
print(c_res)

代码中,我们需要用palceholder先开辟一个内存空间,然后构建好静态计算图后,在把数据赋值到这个被开辟的内存中,然后再运行整个计算流程。

下面我们来看在eager模式下运行上面的代码

import tensorflow as tf
a = tf.Variable(2)
b = tf.Variable(20)
c = a + b

没错,这样的话,就已经完成一个动态计算图的构建,TF2是默认开启eager模式的,所以不需要要额外的设置了。这样的构建方法,和PyTorch是非常类似的。

3 获取导数/梯度

假如我们使用的是PyTorch,那么我们如何得到的导数呢?

import torch
# Create tensors.
x = torch.tensor(10., requires_grad=True)
w = torch.tensor(2., requires_grad=True)
b = torch.tensor(3., requires_grad=True)
# Build a computational graph.
y = w * x + b    # y = 2 * x + 3
# Compute gradients.
y.backward()
# Print out the gradients.
print(x.grad)    # tensor(2.)
print(w.grad)    # tensor(10.)
print(b.grad)    # tensor(1.)

都没问题吧,下面用Tensorflow2.0来重写一下上面的内容:

import tensorflow as tf
x = tf.convert_to_tensor(10.)
w = tf.Variable(2.)
b = tf.Variable(3.)
with tf.GradientTape() as tape:
    z = w * x + b
dz_dw = tape.gradient(z,w)
print(dz_dw)
>>> tf.Tensor(10.0, shape=(), dtype=float32)

我们需要注意这几点:

  • 首先结果来看,没问题,w的梯度就是10;
  • 对于参与计算梯度、也就是参与梯度下降的变量,是需要用tf.Varaible来定义的;
  • 不管是变量还是输入数据,都要求是浮点数float,如果是整数的话会报错,并且梯度计算输出None;d38afb8f8a6c9fa2eefecf3cd244a5b1.png
  • tensorflow提供tf.GradientTape来实现自动求导,所以在tf.GradientTape内进行的操作,都会记录在tape当中,这个就是tape的概念。一个摄影带,把计算的过程录下来,然后进行求导操作

现在我们不仅要输出w的梯度,还要输出b的梯度,我们把上面的代码改成:

import tensorflow as tf
x = tf.convert_to_tensor(10.)
w = tf.Variable(2.)
b = tf.Variable(3.)
with tf.GradientTape() as tape:
    z = w * x + b
dz_dw = tape.gradient(z,w)
dz_db = tape.gradient(z,b)
print(dz_dw)
print(dz_db)

运行结果为:265e4e20fc953a8a22853d9b509cfd20.png

这个错误翻译过来就是一个non-persistent的录像带,只能被要求计算一次梯度。 我们用tape计算了w的梯度,然后这个tape清空了数据,所有我们不能再计算b的梯度。

解决方法也很简单,我们只要设置这个tape是persistent就行了:

import tensorflow as tf
x = tf.convert_to_tensor(10.)
w = tf.Variable(2.)
b = tf.Variable(3.)
with tf.GradientTape(persistent=True) as tape:
    z = w * x + b
dz_dw = tape.gradient(z,w)
dz_db = tape.gradient(z,b)
print(dz_dw)
print(dz_db)

运行结果为:de6499e661506627467a1646c1b9fbc1.png

4 获取高阶导数

import tensorflow  as tf
x = tf.Variable(1.0)
with tf.GradientTape() as t1:
    with tf.GradientTape() as t2:
        y = x * x * x
    dy_dx = t2.gradient(y, x)
    print(dy_dx)
d2y_d2x = t1.gradient(dy_dx, x)
print(d2y_d2x)
>>> tf.Tensor(3.0, shape=(), dtype=float32)
>>> tf.Tensor(6.0, shape=(), dtype=float32)

想要得到二阶导数,就要使用两个tape,然后对一阶导数再求导就行了。

- END - <>

小白学论文 | EfficientNet强在哪里

小白学论文 | 神经网络初始化Xavier

小白学论文 | 端侧神经网络GhostNet(2019)

小白学目标检测 | RCNN, SPPNet, Fast, Faster

小白学图像 | BatchNormalization详解与比较

小白学图像 | Group Normalization详解+PyTorch代码

小白学图像 | 八篇经典CNN论文串讲

图像增强 | CLAHE 限制对比度自适应直方图均衡化

小白学卷积 | 深入浅出卷积网络的平移不变性

小白学卷积 | (反)卷积输出尺寸计算

损失函数 | 焦点损失函数 FocalLoss 与 GHM

<>

小白学ML | 随机森林 全解 (全网最全)

小白学SVM | SVM优化推导 + 拉格朗日 + hingeLoss

小白学LGB | LightGBM = GOSS + histogram + EFB

小白学LGB | LightGBM的调参与并行

小白学XGB | XGBoost推导与牛顿法

评价指标 | 详解F1-score与多分类F1

小白学ML | Adaboost及手推算法案例

小白学ML | GBDT梯度提升树

小白学优化 | 最小二乘法与岭回归&Lasso回归

小白学排序 | 十大经典排序算法(动图)

杂谈 | 正态分布为什么如此常见

Adam优化器为什么被人吐槽?

机器学习不得不知道的提升技巧:SWA与pseudo-label

<>

秋招总结 | 一个非Top学校的跨专业的算法应届研究生的几十场面试

【小白面经】快手 AI算法岗 附答案解析

【小白面经】 拼多多 AI算法岗 附带解析

【小白面经】八种应对样本不均衡的策略

【小白面经】之防止过拟合的所有方法

【小白面经】梯度消失爆炸及其解决方法

【小白面经】 判别模型&生成模型

<>

【小白健身】腹肌搓衣板化

【小白健身】8个动作练爆胸大肌

【小白健身 】背阔大作战(下)

【小白健身】背阔大作战(上)

【小白健身】徒手健身40个动作(gif)

【小白健身】弹力带轻度健身gif动图

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值