神经网络,可以看做是一个非常复杂的公式的代码实现。计算机没法理解抽象的公式,需要我们翻译翻译。例如 y = 10 x + 3 y = 10x + 3 y=10x+3这个公式,我们想让计算机能用它来做计算,我们需要用编程语言做个转换,C++实现如下:
template<class T> T linear(T x) {
T a = 10; T b = 3; return a * x + b; }
这个公式最终是平面中一系列的点所组成的一条直线。
当来到神经网络这个非常复杂的公式,最终你会在一个超空间里表现出一个我们无法想象的平面。我们每一条数据,都可以看成是一个超空间里面的点,所有数据在一起应该会组成一个超平面。神经网络的目的就是企图找到这个超平面。搭建模型的过程,就是提供一个有潜力拟合这个超平面的一部分的过程;训练的过程就是让这个公式尝试去拟合这个超平面的一部分的过程。通过训练,合适的模型最终会拟合一条曲线、平面、超平面一部分。为什么说是一部分呢,因为数据是有限的,我们所找到的这个公式也许最终也只是在我们所给出的数据范围内能够拟合这个超平面。超平面是固有的,公式是我们试图对这个超平面的复现。
神经网络经过学习,可以将一种信息转换成另信息的另一种描述。例如将一张猫的图片转换为“猫”这个文字。因为信息在神经网络中都是以浮点数来表现的,我们需要把我们的信息都转化到浮点数上来(定点也行,不过原理都一样)。这样我们的每一条数据就能表现为超平面上的一个点了。
信息转换成浮点数值之后,还需要有一个数据结构来存储,并且计算的中间结果也是一些浮点数,也需要一个数据结构来存储。
通常,经过转换的信息和计算的中间结果都会表现为一个多维数组,例如可以用一个三维数组表示图片、四维数组表示视频等。
虽然Python中的List可以表示多维数组,但是神经网络中一般不会使用List去存储数据,原因主要有以下几点:
首先,Python List是一个对象的集合,它可以存储任何对象,即便存储的是浮点数值,每一个浮点数值都经过对应Python对象的封装,添加了额外的空间去保存引用计数等信息,这会造成很多空间了浪费,并且离散的分布在内存中,不利于进行优化;
其次,Python List是没有定义有对其所表示的向量、矩阵等的点乘等操作,这些操作在神经网络中是基本的操作;
再有,对List的操作需要通过Python解析器来完成,相对于直接执行机器指令而言,这种方法速度是非常慢的。
这些缺点对于需要进行密集计算的神经网络来说,是无法忍受的。因此,需要一个便捷、高效的数据结构来存储计算过程中的中间数据等多维数组。不同的框架可能称呼不一样,例如在NumPy中称为ndarray。而在PyTorch中这个专门的数据结构称为Tensor。
Tensor(张量),可能在物理等其他领域表示的意义略有差别,但在计算机中的表现形式其实就是一个多维数组,就类似于一维数组称被称为向量、二维数组被称为矩阵一样。
Tensor的底层是用C/C++实现的,它不仅用于存储数据,还定义了对数据的操作。抛开这些不说,它与Python List最大的区别就是它使用一个连续的内存区域去存储数据,并且这些数据并未经过封装。Python List 和Tensor的区别如图2所示:
在图2中,左边表示Python List,可以看到每个数值类型都被封装成了一个PyObject对象,每个对象是独立分配内存、离散的存储在内存中;右边表示Tensor,Tensor中的数值统一的保存在一块连续的内存中,而且是不经过封装的。
你以为你已经看到Tensor的内部原理了?不,你没有。
真正管理存储这数据的内存区域的,是类Storage
的实例,这个Storage
的实例通过一个一维数组来存储数据。你没看错,是一维数组。不管外在表现为多少维的数组,都是存储在一个一维数组中。而怎么让这个一维数组看起来像多维数组,就是Tensor完成的。其内部实现关系如图3所示。
Storage
类中有一个指针指向存储数据的一位数组,而Tensor
通过对Storage
进行封装,使得在外部看来数据是多维的。
多个Tensor
的实例可以指向同一个Storage
,例如下面的代码:
import torch a = torch.tensor([[4,1,5],[3,2,1]]) print(a.storage()) ar = a.reshape((3,2)) print(ar.storage()) at = a.transpose(1,0) print(at.storage())
输出如下:
4 1 5 3 2 1 [torch.LongStorage of size 6] 4 1 5 3 2 1 [torch.LongStorage of size 6] 4 1 5 3 2 1 [torch.LongStorage of size 6]
他们看起来是不同的Tensor
,但是指向的却是同一个Storage
,如果你该表其中一个的内容,另一个Tensor
也会随之改变,例如,我们将上面例子中ar
的第二行第一个元素的值变成100
,看看会发生什么:
ar[1,1] = 100 print(a.storage()) print(ar.storage()) print(at.storage
到此这篇pytorch框架解读的文章就介绍到这了,更多相关内容请继续浏览下面的相关推荐文章,希望大家都能在编程的领域有一番成就!
版权声明:
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若内容造成侵权、违法违规、事实不符,请将相关资料发送至xkadmin@xkablog.com进行投诉反馈,一经查实,立即处理!
转载请注明出处,原文链接:https://www.xkablog.com/rgzn-ptkj/5015.html