先提第二部分,第一部分放后面了(如果没了解过深度学习的童鞋可以从第一部分开始看起)~
在开始学习前可以先看一副来自nndl的思维导图:
文章目录
- 1.张量
- 视频数据
- 一个有趣比喻
- 附工具使用:
- 简介
学习Keras之父Francois Chollet的《python深度学习》第2章
第二部分:深度学习的数学基础
一.初识神经网络
MNIST数字图像样本-过程介绍:
(1)加载Keras中的MNIST数据集
(2)网络架构
网络中包含2个Dense层,即(全连接)的神经层。第二层(即最后一层)是一个10路softmax层(将返回一个由10个概率值,总和为1)的数组,每个概率值表示当前数字图像属于10个数字类别中某一个的概率。
(3)编译:损失函数、优化器、在训练和测试中需要监控的指标
(4)准备图像数据
(5)准备标签
二.神经网络的数据表示
所有机器学习系统都用【张量】作为基本数据结构。
张量是一个数据容器,包含的数据几乎总是数值数据。矩阵就是一个二维张量。
轴:张量的维度。
1.张量
标量:仅含1个数字的张量,又叫标量张量、零维张量、0D张量。
阶:张量轴的个数。
1.1向量(1D张量)
向量?:数组组成的数组。又叫一维张量(1D张量)。
该向量有5个元素,即叫5D向量。
区分:5D向量和5D张量
5D向量:只有一个轴,沿着轴有5个维度;上面的1D张量就是一个向量,该向量有5个元素,所以称为5D向量。
5D张量:有5个轴(沿着每个轴可能有任意个维度)
1.2矩阵(2D张量)
上面为形状为(3,5)的矩阵
矩阵有个2个轴,第一个轴上的元素叫做行,第二个轴上的元素叫做列。
1.3 3D张量与更高维张量
上面张量的形状为(3,3,5)
上面的3D张量可以直观理解为数字组成的立方体,深度学习处理一般是0D到4D的张量(但处理视频数据可能会遇到5D张量)。
还有很多函数可以创建Tensor,去翻翻官方API就知道了,下表给了一些常用的作参考。
函数 | 功能 |
Tensor(*sizes) | 基础构造函数 |
tensor(data,) | 类似np.array的构造函数 |
ones(*sizes) | 全1Tensor |
zeros(*sizes) | 全0Tensor |
eye(*sizes) | 对角线为1,其他为0 |
arange(s,e,step) | 从s到e,步长为step |
linspace(s,e,steps) | 从s到e,均匀切分成steps份 |
rand/randn(*sizes) | 均匀/标准分布 |
normal(mean,std)/uniform(from,to) | 正态分布/均匀分布 |
randperm(m) | 随机排列 |
这些创建方法都可以在创建的时候指定数据类型dtype和存放device(cpu/gpu)。
2.关键属性
(1)轴的个数(阶):如3D张量有3个轴,即张量的ndim
(2)形状:一个整数元组,表示张量沿着每个轴的维度大小(元素个数)
向量的形状只包含一个元素,如(5,),而标量的形状为空,即()
(3)数据类型:在python库中叫做dtype,张量的类型是float32、uint8等
Numpy中不存在字符串张量(因为张量存储在预先分配的连续内存段中,而字符串的长度是可变的)
3.在Numpy中操作张量
Numpy数组上的张量切片()
过程和python中的列表索引差不多,如果是负数,如-7则表示倒数第7个元素
如上面的MNIST例子中在图像中心裁剪出14像素 × 14像素的区域
4.数据批量的概念
通常来说,深度学习中所有数据张量的第一个轴(0 轴,因为索引从 0 开始)都是样本轴
(samples axis,有时也叫样本维度)。在 MNIST 的例子中,样本就是数字图像。
此外,深度学习模型不会同时处理整个数据集,而是将数据拆分成小批量。
5.现实世界中的数据张量
(1)向量数据:2D 张量,形状为 (samples, features)。
(2)时间序列数据或序列数据:3D 张量,形状为 (samples, timesteps, features)。
(3)图像:4D 张量,形状为 (samples, height, width, channels) 或 (samples, channels, height, width)。
(4)视频:5D 张量,形状为 (samples, frames, height, width, channels) 或 (samples, frames, channels, height, width)。
上面的向量数据是最常见的数据:
每个数据点都被编码为一个向量,即一个数据批量就被编码为2D张量(即向量组成的数组)
第一个轴:样本轴
第二个轴:特征轴
小栗子:人口统计数据集
(10000, 3)的2D张量:
整个数据集中包含10000人,每个人可以表示为包含3个值(年龄、邮编和收入)的向量。
6.时间序列数据or序列数据
2个简单例子:
(250, 290, 3)的3D张量可以表示为:股票价格数据集
250天的数据,每个样本数据是一天的股票数据,一个交易日有390分钟(每分钟保存的是股票的当前价格、前一分钟的最高价格、前一分钟的最低价格)
(1000000, 280, 128)的3D张量可以表示为:1000000条推文的数据集
其中每条推文为280个字符组成的序列,每个字符来自128个字符组成的字母表(即每个字符可以编码为size为128的二进制向量,只有该字符对应的索引位置取1,其他元素为0)
7.图像数据 & 视频图像
图像数据
(128,256,256,3)的张量可以表示128张彩色图像(图像大小为256 ×256)组成的批量(3是3中颜色通道)
上图为通道在前的约定。
图像张量的形状有2种约定
Keras框架同时支持这两种格式
(1)通道在后(),在TensorFlow中使用
(samples, height, width, color_depth)
(2)通道在前(),在Theano中使用
(samples, color_depth, height, width)
视频数据
视频可以看作一系列帧,每一帧都是一张彩色图像。由于每一帧都可以保存在一个形状为 (height, width, color_depth) 的 3D 张量中,因此一系列帧可以保存在一个形状为 (frames, height, width, color_depth) 的 4D 张量中,而不同视频组成的批量则可以保存在一个 5D 张量中,其形状为(samples, frames, height, width, color_depth)。
三.神经网络的“齿轮”:张量运算
深度神经网络的所有变化可以简化为数值数据张量上的一些张量运算,如加上张量、乘以张量等
3.1逐元素运算
relu(x) 是 max(x, 0),如对逐元素relu
运算的简单实现:
如果在Numpy中逐元素运算就更简单了:
3.2广播
假设 X 的形状是 (32, 10),y 的形状是 (10,)。首先,我们给 y添加空的第一个轴,这样 y 的形状变为 (1, 10)。然后,我们将 y 沿着新轴重复 32 次,这样得到的张量 Y 的形状为 (32, 10),并且 Y[i, :] == y for i in range(0, 32)。现在,我们可以将 X 和 Y 相加,因为它们的形状相同。
如果一个张量的形状是 (a, b, … n, n+1, … m),另一个张量的形状是 (n, n+1, … m),那么你通常可以利用广播对它们做两个张量之间的逐元素运算。广播操作会自动应用于从 a 到 n-1 的轴。
3.3张量点积
在Numpy和Keras中,都是用标准的dot
运算符实现点积。
x和y的点积的计算过程:
3.4张量变形
还有一种张量变形是转置,使x[i, :]
变为x[:, i]
:
3.5张量的几何解释
仿射变换、旋转、缩放等的几何操作都可以表示为张量运算。
要将一个二维向量旋转theta角,可以通过与一个2 × 2矩阵做点积实现,这个矩阵为 R = [u, v],其
中 u 和 v 都是平面向量:u = [cos(theta), sin(theta)],v = [-sin(theta), cos(theta)]。
3.6深度学习的几何解释
神经网络完全由一系列张量运算组成,而这些张量运算都只是输入数据的几何变换。因此,你可以将神经网络解释为高维空间中非常复杂的几何变换,这种变换可以通过许多简单的步骤来实现。
一个有趣比喻
对于三维的情况,下面这个思维图像是很有用的。想象有两张彩纸:一张红色,一张蓝色。
上面两张纸揉成一团,神经网络(或者任何机器学习模型)要做的就是找到可以让纸球恢复平整的变换,从而能够再次让两个类别明确可分。通过深度学习,这一过程可以用三维空间中一系列简单的变换来实现,比如你用手指对纸球做的变换,每次做一个动作。
让纸球恢复平整就是机器学习的内容:为复杂的、高度折叠的数据流形找到简洁的表示。
为什么深度学习特别擅长这一点:它将复杂的几何变换逐步分解为一长串基本的几何变换,这与人类展开纸球所采取的策略大致相同。深度网络的每一层都通过变换使数据解开一点点——许多层堆叠在一起,可以实现非常复杂的解开过程。
四.神经网络的“引擎”:基于梯度的优化
最初栗子中,我们通过叠加Dense层构建网络,Keras层的实例如下:
这个层可以理解为一个函数,输入一个2D张量,返回两一个2D张量(输入张量的新表示)。
每个神经层都用下面函数对输入数据进行变换,具体的函数如下:
(W为一个2D张量,b为一个2D向量,都是该层的属性,被称为该层的【权重】或【可训练参数】,分别对应kernel和bias属性)
随机初始化
——》训练(根据反馈信号逐渐调整这些权重)
——》训练循环
——》最终得到的网络再训练数据上的损失非常小(即预测值和预测目标的绝对值小)
可以知道【训练循环】的过程如下:
(1) 抽取训练样本 x 和对应目标 y 组成的数据批量。
(2) 在 x 上运行网络[这一步叫作前向传播(forward pass)],得到预测值 y_pred。
(3) 计算网络在这批数据上的损失,用于衡量 y_pred 和 y 之间的距离。
(4) 难点:更新网络的所有权重,使网络在这批数据上的损失略微下降。
对于(4)一种简单的解决方案是,保持网络中其他权重不变,只考虑某个标量系数,让其尝试不同的取值。假设这个系数的初始值为 0.3。对一批数据做完前向传播后,网络在这批数据上的损失是 0.5。如果你将这个系数的值改为 0.35 并重新运行前向传播,损失会增大到 0.6。但如果你将这个系数减小到 0.25,损失会减小到 0.4。在这个例子中,将这个系数减小 0.05 似乎有助于使损失最小化。对于网络中的所有系数都要重复这一过程。
但这种方法是非常低效的,因为对每个系数(系数很多,通常有上千个,有时甚至多达上百万个)都需要计算两次前向传播(计算代价很大)。一种更好的方法是利用网络中所有运算都是可微(differentiable)的这一事实,计算损失相对于网络系数的梯度(gradient),然后向梯度的反方向改变系数,从而使损失降低。
4.1张量运算的导数:梯度
梯度:张量运算的导数,梯度在高数下册也学过,梯度是一个向量,而这个向量的模等于在该点处方向导数最大值。
4.2随机梯度下降
核心思想:随机抽取若干个数据点,用这若干个点的梯度平均值去估计损失函数的梯度。
——数学上可证明,这样能保证函数达到局部最低点。
训练轮次epoch:数据将被用几遍
4.3链式求导:反向传播算法
反向传播(也叫反式微分):将链式法则应用于【损失函数对每个参数的偏导数计算】
反向传播从最终损失值开始,从最顶层反向作用至最底层,利用链式法则计算每个参数对损失值的贡献大小。
五.回顾第一个例子
1.输入数据
输入图像保存在 float32 格式的 Numpy 张量中,形状分别为 (60000, 784)(训练数据)和 (10000, 784)(测试数据)
2.构建网络
这个网络包含两个 Dense 层,每层都对输入数据进行一些简单的张量运算,这些运算都包含权重张量。权重张量是该层的属性,里面保存了网络所学到的知识(knowledge)。
3.网络的编译
categorical_crossentropy 是损失函数,是用于学习权重张量的反馈信号,在训练阶段应使它最小化。你还知道,减小损失是通过小批量随机梯度下降来实现的。
梯度下降的具体方法由第一个参数给定,即 rmsprop 优化器。
4.训练循环
现在你明白在调用 fit 时发生了什么:网络开始在训练数据上进行迭代(每个小批量包含128 个样本),共迭代 5 次[在所有训练数据上迭代一次叫作一个轮次(epoch)]。在每次迭代过程中,网络会计算批量损失相对于权重的梯度,并相应地更新权重。5 轮之后,网络进行了2345 次梯度更新(每轮 469 次),网络损失值将变得足够小,使得网络能够以很高的精度对手写数字进行分类。
在tensorflow上训练得到的结果如下所示:
本章小结
(1)学习是指找到一组模型参数,使得在给定的训练数据样本和对应目标值上的损失函数最小化。
(2)学习的过程:随机选取包含数据样本及其目标值的批量,并计算批量损失相对于网络参数的梯度。随后将网络参数沿着梯度的反方向稍稍移动(移动距离由学习率指定)。
(3)整个学习过程之所以能够实现,是因为神经网络是一系列可微分的张量运算,因此可以利用求导的链式法则来得到梯度函数,这个函数将当前参数和当前数据批量映射为一个梯度值。
(4)重要概念:损失和优化器。将数据输入网络之前,你需要先定义这二者。
损失:在训练过程中需要最小化的量,因此,它应该能够衡量当前任务是否已成功解决。
优化器:使用损失梯度更新参数的具体方式,比如 RMSProp 优化器、带动量的随机梯度下降(SGD)等。
=====================================================
学习Keras之父Francois Chollet的《python深度学习》第一章
第一部分:深度学习初探
一.AI ML DL
1.ML
ML和传统编程不同,ML系统是训练出来。
ML常用于处理复杂的大型数据集(如百万张图像数据集,每张图像又包含数万个像素),用经典的统计分析(如贝叶斯分析)来处理这种数据集难以实现。
3.从数据中学习表示
ML三要素:
输入数据点,预期输出的示例,衡量算法效果好坏的算法。
ML和DL的核心问题:有意义地变换数据,即学习输入数据的有用表示,让数据更接近预期输出。
表示:以一种不同的方式表征数据或将数据编码,如彩色图片可以编码为RGB(红-绿-蓝)格式或者HSV(色相=饱和度-明度)格式,而在处理“选择图像中所有红色像素”任务中,用RGB格式会更简单,而处理“降低图像饱和度”任务中,用HSV格式会更简单。
ML技术定义:在预先定义好的可能性空间中,利用反馈信号的指引来寻找输入数据的有用表示
4.深度学习之深度
深度表示一系列连续的表示层
ps:没有虽然DL一些核心概念是从人们对大脑的理解中获取灵感形成的,但是没有证据表明大脑的学习机制与现代DL模型相同。即DL是从数据中学习表示的一种数学框架。
DL技术定义: 学习数据表示的多级方法。即可将深度网络看做多级信息蒸馏操作:信息穿过连续的过滤器,其纯度越来越高。
5.三张图理解DL工作原理
ML是将输入(如图片)映射到目标(如标签:猫),这一过程是通过观察许多输入和目标的示例完成;DL是通过一系列数据变换层实现这种输入到目标的映射,这些数据变换也都是通过观察示例学习到的。
(1)DL是由其权重来参数化
(2)损失函数用来衡量网络输出结果的质量
(3)将损失值作为反馈信号来调节权重
6.DL进展
深度学习已经取得了以下突破,它们都是机器学习历史上非常困难的领域:
‰ 接近人类水平的图像分类
‰ 接近人类水平的语音识别
‰ 接近人类水平的手写文字转录
‰ 更好的机器翻译
‰ 更好的文本到语音转换
‰ 数字助理,比如谷歌即时(Google Now)和亚马逊 Alexa
‰ 接近人类水平的自动驾驶
‰ 更好的广告定向投放,Google、百度、必应都在使用
‰ 更好的网络搜索结果
‰ 能够回答用自然语言提出的问题
‰ 在围棋上战胜人类
我们仍然在探索深度学习能力的边界。我们已经开始将其应用于机器感知和自然语言理解
之外的各种问题,比如形式推理。
7.唠嗑
二.DL之前:ML简史
若第一次接触的ML就是DL,可能会陷入误区,唯一方法是熟悉其他ML并在适当时候实践。
又是没有足够的数据,DL不合适或者其他算法能更好解决问题。
1.概率建模
概率建模是统计学的东西,朴素贝叶斯算法就是一种机器学习分类器:
假设输入数据的特征都是独立的——朴素的假设
logistic回归(logistic regression
)是一种分类算法,不要被名字误导(不是回归算法),和朴素贝叶斯一样,逻辑回归比计算机的出现还早很多,但因为简单使用,如今仍很用。
2.早期神经网络
1980+反向传播算法——利用梯度下降优化训练一系列参数化运算链
1989将CNN和反向传播算法结合,应用手写数字分类
3.核方法
核方法是一组分类方法,最出名即SVM
SVM目标通过属于两个不同类别的两组数据点之间找到良好决策边界
4.决策树、随机森林与梯度提升机
kaggle在2010年上线后,随机森林成为人们最爱,到了2014年才背梯度提升机()取代
5.回到DL
DL让特征工程完全自动化(特征工程:让初始输入数据更适合用这些方法处理,也必须手动为数据设计好的表示层)
2015 2016年的CV会议上几乎都与深度卷积神经网络(convnet)有关
深度学习已经在大量应用中完全取代了SVM与决策树,如欧洲核子研究中心就从决策树专项基于Keras的深度神经网络分析大型强子对撞机的粒子数据。
6.DL有何不同,DL现状
ML(浅层学习)仅包含将输入数据变换到一两个连续的表示空间,通常用简单的变换,如SVM或者决策树——无法得到复杂问题所需要的精确表示。
DL从数据中进行学习有2个基本特征:
(1)通过渐进的、逐层的方式形成越来越复杂的表示
(2)对中间这些渐进的表示共同进行学习,每一层的变化都需要同时考虑上下两层的需要
了解ML现状的好方法:看下kaggle竞赛——哪种算法能获胜,顶级参赛者用哪些工具
2016和2017年kaggle注意两大方法:梯度提升机和深度学习
梯度提升机:处理结构化数据,用XGBoost库(支持python和R)
深度学习:图像分类等感知问题,大多用Keras库(支持python)
DL用于CV的两个关键思想(CNN和反向传播),1989年
长短期记忆LSTM()算法是深度学习处理时间序列的基础,1997年
现在——DL牛逼因为:
(1)硬件:互联网高速发展,针对游戏市场的需求开发出高性能能图形芯片,深度学习行业也开始超过GPU,如2016年google的张量处理器TPU,速度最好的GPU快10倍
(2)数据:如Flickr网站上用户生成的图像标签、youtube是CV的数据宝库,维基百科是NLP的关键数据集。
(3)算法:2009-2010年出现几个很简单却很重要的算法改进,实现更好的梯度传播,改进:
更好的神经层激活函数、权重初始化方案,更好的优化方案如RMSProp和Adam
2014-2016年更先进的助于梯度传播的方法:批标准化、残差连接和深度可分离卷积,如今我们可训练上千层的模型。
DL大众化
早期深度学习需要精通C++和CUDA,现在会python,theano,TensorFlow和keras
theano和TensorFlow是2个符号式的张量运算的python框架,都支持自动求微分(化简新模型的实现过程),而Keras在2015年发布后也受深度学习学习者热捧
DL会持续
20 年后我们可能不再使用神经网络,但我们那时所使用的工具都是直接来自于现代深度学习及其核心概念。
(1)简单。深度学习不需要特征工程,它将复杂的、不稳定的、工程量很大的流程替换为简单的、端到端的可训练模型,这些模型通常只用到五六种不同的张量运算。
(2)可扩展。深度学习非常适合在GPU或TPU上并行计算,因此可以充分利用摩尔定律。此外,深度学习模型通过对小批量数据进行迭代来训练,因此可以在任意大小的数据集上进行训练。(唯一的瓶颈是可用的并行计算能力,而由于摩尔定律,这一限制会越来越小。)
(3)多功能与可复用。与之前的许多机器学习方法不同,深度学习模型无须从头开始就可以在附加数据上进行训练,因此可用于连续在线学习,这对于大型生产模型而言是非常重要的特性。此外,训练好的深度学习模型可用于其他用途,因此是可以重复使用的。举个例子,可以将一个对图像分类进行训练的深度学习模型应用于视频处理流程。这样我们可以将以前的工作重新投入到日益复杂和强大的模型中。这也使得深度学习可以适用于较小的数据集。
附工具使用:
1.anaconda
https://www.jianshu.com/p/1c444f00986b更换源
在(https://mirrors.tuna.tsinghua.edu.cn/anaconda/archive/Anaconda3-2021.05-Windows-x86_64.exe)anaconda下载好后:
(1)首先搞一个虚拟环境,所有库都在这个虚拟环境中下载好,运行就用这个虚拟环境对应的jupyter
(2)调整navigator的界面大小
vim /home/xxx/.anaconda/navigator/anaconda-navigator.ini
把27行改成这个enable_high_dpi_scaling = False
在prompt的操作:
(0)新建一个虚拟环境:conda create --name python38-env
(1)查看已有的虚拟环境:conda env list
(2)切换到想要去的环境,如my_test:conda activate my_test
(3)在当前环境里安装ipykernel:conda install ipykernel
(4)在python38-env虚拟环境中使用py3.8:conda create --name python38-env python=3.8
简介
Anaconda 已经预先安装好 NumPy、SciPy、matplotlib、pandas、IPython、Jupyter Notebook 和 scikit-learn。其中sklearn依赖于另外两个python包:NumPy和SciPy
在sklearn中NumPy数组是基本数据结构,即你用到的所有数据都必须转换成NumPy数组——NumPy的核心功能是ndarray类(n维数组)。数组的所有元素必须是同一类型。
2.修改navigator的虚拟环境名
怎么对虚拟环境改名字呢?
windows平台,找到当前主用户文件夹,有一个.conda文件夹,里面有一个environments.txt文件。找不到.conda文件夹的可以设置查看隐藏目录。
比如C:\Users"your username".conda\environments.txt。
再打开你安装anaconda的目录,找到envs文件夹,里面就是你的虚拟环境。
修改方法:直接修改envs下的你想修改的环境名称,然后将environments.txt中的环境列表名称对应修改即可。注意:一定要保证一致
3.jupyter notebook中cell
(1)三种cell类型:
code(编辑代码,运行后出现代码结果)
markdown(运行后输出markdown文档)
raw NBConvert(普通文本,运行不会出现结果)
(2)jupyter两种模式
编辑模式(Enter)
- 命令模式下回车Enter或鼠标代码块进入编辑模式
- 可以操作代码或文本,进行剪切 / 复制 / 粘贴等操作
命令模式(Esc) - 按Esc退出编辑,进入命令模式或单击代码块外部
- 可以操作cell单元本身,进行剪切 / 复制 / 粘贴/移动等操作
(3)工具栏操作cell
4.tensorflow
5.pytorch
下载中报错:出现CondaHTTPError: HTTP 000 CONNECTION FAILED for url … 处理方法 添加清华源:https://www.it610.com/article/1290197727942090752.htm
reference
Keras之父Francois Chollet的《python深度学习》