深入浅出PyTorch_2_基础知识

[toc]

张量(Tensor)

概念

几何代数中定义的张量是基于向量和矩阵的推广,比如我们可以将标量视为零阶张量,矢量可以视为一阶张量,矩阵就是二阶张量。

  • 0维张量/标量 标量是一个数字
  • 1维张量/向量 1维张量称为“向量”。
  • 2维张量 2维张量称为矩阵
  • 3维张量 公用数据存储在张量 时间序列数据 股价 文本数据 彩色图片(RGB)

张量是现代机器学习的基础。它的核心是一个数据容器,多数情况下,它包含数字,有时候它也包含字符串,但这种情况比较少。因此可以把它想象成一个数字的水桶。

这里有一些存储在各种类型张量的公用数据集类型:

  • 3维=时间序列
  • 4维=图像
  • 5维=视频

例子:一个图像可以用三个字段表示:

(width, height, channel) = 3D

相关操作

创建tensor

构造一个随机初始化的矩阵:

from __future__ import print_function
import torch

x = torch.rand(4, 3) 
print(x)

构造一个矩阵全为 0,而且数据类型是 long.

x = torch.zeros(4, 3, dtype=torch.long)
print(x)
tensor([[0, 0, 0],
        [0, 0, 0],
        [0, 0, 0],
        [0, 0, 0]])

直接使用数据,构造一个张量:

x = torch.tensor([5.5, 3]) 
print(x)
tensor([5.5000, 3.0000])

基于已经存在的 tensor,创建一个 tensor :

x = x.new_ones(4, 3, dtype=torch.double) # 创建一个新的tensor,返回的tensor默认具有相同的 torch.dtype和torch.device
# 也可以像之前的写法 x = torch.ones(4, 3, dtype=torch.double)
print(x)
x = torch.randn_like(x, dtype=torch.float)
# 重置数据类型
print(x)
# 结果会有一样的size
tensor([[1., 1., 1.],
        [1., 1., 1.],
        [1., 1., 1.],
        [1., 1., 1.]], dtype=torch.float64)
tensor([[ 0.2626, -0.6196,  1.0963],
        [ 1.1366, -0.6543,  0.6040],
        [-0.6623,  0.1115,  0.2433],
        [ 1.1626, -2.3529, -0.9417]])

获取它的维度信息:

print(x.size())
print(x.shape)
torch.Size([4, 3])

返回的torch.Size其实就是一个tuple,⽀持所有tuple的操作。

还有一些常见的构造Tensor的函数:

函数 功能
Tensor(*sizes) 基础构造函数
tensor(data) 类似于np.array
ones(*sizes) 全1
zeros(*sizes) 全0
eye(*sizes) 对角为1,其余为0
arange(s,e,step) 从s到e,步长为step
linspace(s,e,steps) 从s到e,均匀分成step份
rand/randn(*sizes)
normal(mean,std)/uniform(from,to) 正态分布/均匀分布
randperm(m) 随机排列

三角函数

torch.abs(input, out=None)
torch.acos(input, out=None)
torch.asin(input, out=None)
torch.atan(input, out=None)
torch.atan2(input, inpu2, out=None) 
torch.cos(input, out=None)
torch.cosh(input, out=None)
torch.sin(input, out=None)
torch.sinh(input, out=None)
torch.tan(input, out=None)
torch.tanh(input, out=None)

基本运算,加减乘除

Torch.add(input, value, out=None)
          .add(input, value=1, other, out=None)
          .addcdiv(tensor, value=1, tensor1, tensor2, out=None)
          .addcmul(tensor, value=1, tensor1, tensor2, out=None)
torch.div(input, value, out=None)
         .div(input, other, out=None)
torch.mul(input, value, out=None)
        .mul(input, other, out=None)

对数运算

torch.log(input, out=None)  # y_i=log_e(x_i)
torch.log1p(input, out=None)  #y_i=log_e(x_i+1)
torch.log2(input, out=None)   #y_i=log_2(x_i)
torch.log10(input,out=None)  #y_i=log_10(x_i)

幂函数

torch.pow(input, exponent, out=None)  # y_i=input^(exponent)

指数运算

torch.exp(tensor, out=None)    #y_i=e^(x_i)
torch.expm1(tensor, out=None)   #y_i=e^(x_i) -1

截断函数

torch.ceil(input, out=None)   #返回向正方向取得最小整数
torch.floor(input, out=None)  #返回向负方向取得最大整数

torch.round(input, out=None)  #返回相邻最近的整数,四舍五入

torch.trunc(input, out=None)  #返回整数部分数值
torch.frac(tensor, out=None)  #返回小数部分数值

torch.fmod(input, divisor, out=None)  #返回input/divisor的余数
torch.remainder(input, divisor, out=None)  #同上

其他运算

torch.erf(tensor, out=None)
 
torch.erfinv(tensor, out=None)
 
torch.sigmoid(input, out=None)
 
torch.clamp(input, min, max out=None)  #返回 input<min,则返回min, input>max,则返回max,其余返回input

torch.neg(input, out=None) #out_i=-1*(input)

torch.reciprocal(input, out=None)  # out_i= 1/input_i

torch.sqrt(input, out=None)  # out_i=sqrt(input_i)
torch.rsqrt(input, out=None) #out_i=1/(sqrt(input_i))

torch.sign(input, out=None)  #out_i=sin(input_i)  大于0为1,小于0为-1

torch.lerp(start, end, weight, out=None)

降维操作

torch.argmax(input, dim=None, keepdim=False) #返回最大值排序的索引值
torch.argmin(input, dim=None, keepdim=False)  #返回最小值排序的索引值

torch.cumprod(input, dim, out=None)  #y_i=x_1 * x_2 * x_3 *…* x_i
torch.cumsum(input, dim, out=None)  #y_i=x_1 + x_2 + … + x_i

torch.dist(input, out, p=2)       #返回input和out的p式距离
torch.mean()                      #返回平均值
torch.sum()                       #返回总和
torch.median(input)               #返回中间值
torch.mode(input)                 #返回众数值
torch.unique(input, sorted=False) #返回1-D的唯一的tensor,每个数值返回一次.
>>> output = torch.unique(torch.tensor([1, 3, 2, 3], dtype=torch.long))
>>> output
tensor([ 2,  3,  1])

torch.std(  #返回标准差)
torch.var() #返回方差

torch.norm(input, p=2) #返回p-norm的范式
torch.prod(input, dim, keepdim=False) #返回指定维度每一行的乘积

对比操作

torch.eq(input, other, out=None)  #按成员进行等式操作,相同返回1
torch.equal(tensor1, tensor2) #如果tensor1和tensor2有相同的size和elements,则为true
>>> torch.eq(torch.tensor([[1, 2], [3, 4]]), torch.tensor([[1, 1], [4, 4]]))
tensor([[ 1,  0],
        [ 0,  1]], dtype=torch.uint8)
>>> torch.eq(torch.tensor([[1, 2], [3, 4]]), torch.tensor([[1, 1], [4, 4]]))
tensor([[ 1,  0],
        [ 0,  1]], dtype=torch.uint8)

torch.ge(input, other, out=None)   # input>= other
torch.gt(input, other, out=None)   # input>other
torch.le(input, other, out=None)    # input=<other
torch.lt(input, other, out=None)    # input<other
torch.ne(input, other, out=None)  # input != other 不等于

torch.max()                        # 返回最大值
torch.min()                        # 返回最小值
torch.isnan(tensor) #判断是否为’nan’
torch.sort(input, dim=None, descending=False, out=None) #对目标input进行排序
torch.topk(input, k, dim=None, largest=True, sorted=True, out=None)  #沿着指定维度返回最大k个数值及其索引值
torch.kthvalue(input, k, dim=None, deepdim=False, out=None) #沿着指定维度返回最小k个数值及其索引值

频谱操作

torch.fft(input, signal_ndim, normalized=False)
torch.ifft(input, signal_ndim, normalized=False)
torch.rfft(input, signal_ndim, normalized=False, onesided=True)
torch.irfft(input, signal_ndim, normalized=False, onesided=True)
torch.stft(signa, frame_length, hop, …)

其他操作

torch.cross(input, other, dim=-1, out=None)  #叉乘(外积)

torch.dot(tensor1, tensor2)  #返回tensor1和tensor2的点乘

torch.mm(mat1, mat2, out=None) #返回矩阵mat1和mat2的乘积

torch.eig(a, eigenvectors=False, out=None) #返回矩阵a的特征值/特征向量 

torch.det(A)  #返回矩阵A的行列式

torch.trace(input) #返回2-d 矩阵的迹(对对角元素求和)

torch.diag(input, diagonal=0, out=None) #

torch.histc(input, bins=100, min=0, max=0, out=None) #计算input的直方图

torch.tril(input, diagonal=0, out=None)  #返回矩阵的下三角矩阵,其他为0

torch.triu(input, diagonal=0, out=None) #返回矩阵的上三角矩阵,其他为0

自动微分库

PyTorch 中,所有神经网络的核心是 autograd包。autograd包为张量上的所有操作提供了自动求导机制。它是一个在运行时定义 ( define-by-run )的框架,这意味着反向传播是根据代码如何运行来决定的,并且每次迭代可以是不同的。

autograd.Variable 是这个包中最重要的类。它:

  • 是张量的简单封装
  • 记录了所有历史操作
  • 将梯度保存在 .grad 中
  • 可以帮助建立计算图

[图片上传失败...(image-6ee3bf-1634310841670)]

每次结束计算后,使用.backward()可以自动计算出所有梯度值:

>>> from torch.autograd import Variable
>>> x = torch.randn(3)
>>> x = Variable(x, requires_grad=True)
>>> y = x * 2
>>> while y.data.norm() < 1000:
...     y = y * 2
... 
>>> print(y)
Variable containing:
 908.8007
 549.7198
 507.9812
[torch.FloatTensor of size 3]

# through .data we can access raw tensor
>>> print(y.data)
 908.8007
 549.7198
 507.9812
[torch.FloatTensor of size 3]

# .grad_fn references a Function that has created the Variable 
# (except for Variables created by the user - their grad_fn is None).
>>> print(y.grad_fn)
<MulBackward0 object at 0x7ffa1ea95470>
>>> print(x.grad_fn)
None

# we can call .backward() on a Variable to compute the derivatives. 
# If Variable is a scalar (i.e. it holds a one element data), you don’t need to specify any arguments to backward(), however if it has more elements, you need to specify a gradient argument that is a tensor of matching shape.
>>> gradients = torch.FloatTensor([0.1, 1.0, 0.0001])
>>> y.backward(gradients)
>>> print(x.grad)
Variable containing:
  51.2000
 512.0000
   0.0512
[torch.FloatTensor of size 3]

神经网络

torch.nn包可以用来构建神经网络。一个nn.Module包含了layers和用于返回output的forward(input) 方法。

一般典型的神经网络训练步骤如下:

  1. 定义带学习参数 (learnable parameters or weights) 的神经网络;
  2. 输入数据集进行迭代计算;
  3. 使用神经网络处理输入;
  4. 计算损失;
  5. 将梯度返回到网络的参数中;
  6. 更新参数。

参考资料及相关材料

  1. Awesome-pytorch-list:目前已获12K Star,包含了NLP,CV,常见库,论文实现以及Pytorch的其他项目。
  2. PyTorch官方文档:官方发布的文档,十分丰富。
  3. Pytorch-handbook:GitHub上已经收获14.8K,pytorch手中书。
  4. PyTorch官方社区:在这里你可以和开发pytorch的人们进行交流。
  5. Tensor及其基本操作:罗列了Tensor各项操作
  6. 深入浅出PyTorch学习资料:教程浅显易懂,初学者必备。
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 199,711评论 5 468
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 83,932评论 2 376
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 146,770评论 0 330
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 53,799评论 1 271
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 62,697评论 5 359
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,069评论 1 276
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,535评论 3 390
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,200评论 0 254
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,353评论 1 294
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,290评论 2 317
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,331评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,020评论 3 315
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,610评论 3 303
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,694评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,927评论 1 255
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,330评论 2 346
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 41,904评论 2 341

推荐阅读更多精彩内容