在PyTorch中,torch.Tensor
是存储和变换数据的主要工具。如果你之前用过NumPy,你会发现Tensor
和NumPy的多维数组非常类似。然而,Tensor
提供GPU计算和自动求梯度等更多功能,这些使Tensor
更加适合深度学习。
张量(tensor)是数学和物理学中的概念,它表示任意维度的数组或矩阵。在机器学习和人工智能领域,张量是存储和处理数据的基本数据结构。在深度学习中,张量是神经网络中传递和操作数据的基本单位。它可以是标量(0维张量)、向量(1维张量)、矩阵(2维张量)或更高维度的数组。张量不仅可以包含数字数据,还可以包含其他类型的数据,如字符串、图像等。通过张量,我们可以进行各种数学运算和变换,如加法、乘法、卷积等。深度学习框架如TensorFlow和PyTorch提供了丰富的张量操作函数和工具,使得处理和操作张量变得更加方便和高效。
创建Tensor
在使用深度学习框架(如TensorFlow或PyTorch)时,可以使用相应的函数来创建张量。以下是创建张量的一些常见方法:
- 使用给定值创建张量:
import tensorflow as tf # 创建一个标量(0维张量) scalar = tf.constant(5) # 创建一个向量(1维张量) vector = tf.constant([1, 2, 3]) # 创建一个矩阵(2维张量) matrix = tf.constant([[1, 2, 3], [4, 5, 6]]) # 创建一个3维张量 tensor = tf.constant([[[1, 2], [3, 4]], [[5, 6], [7, 8]]])
- 使用随机值创建张量:
import tensorflow as tf # 创建一个形状为(2, 3)的随机矩阵(2维张量) random_matrix = tf.random.normal(shape=(2, 3)) # 创建一个形状为(3, 3)的随机矩阵(2维张量),数值范围在0到1之间 random_uniform = tf.random.uniform(shape=(3, 3), minval=0, maxval=1)
Tensor
官方API
操作
-
数学运算:
tf.add(x, y)
:逐元素相加。tf.subtract(x, y)
:逐元素相减。tf.multiply(x, y)
:逐元素相乘。tf.divide(x, y)
:逐元素相除。tf.square(x)
:逐元素求平方。tf.sqrt(x)
:逐元素求平方根。tf.exp(x)
:逐元素求指数。tf.log(x)
:逐元素求自然对数。
-
形状操作:
tf.reshape(tensor, shape)
:重新调整张量的形状。tf.transpose(tensor, perm=None)
:交换张量的维度顺序。tf.expand_dims(input, axis=None)
:在指定轴上扩展维度。tf.squeeze(input, axis=None)
:压缩维度为1的轴。tf.concat(tensors, axis)
:沿指定轴连接张量。
-
矩阵操作:
tf.matmul(a, b)
:矩阵相乘。tf.transpose(tensor, perm=None)
:矩阵转置。tf.linalg.inv(tensor)
:矩阵求逆。
-
逻辑运算:
tf.equal(x, y)
:逐元素比较是否相等。tf.not_equal(x, y)
:逐元素比较是否不相等。tf.greater(x, y)
:逐元素比较是否大于。tf.greater_equal(x, y)
:逐元素比较是否大于等于。tf.less(x, y)
:逐元素比较是否小于。tf.less_equal(x, y)
:逐元素比较是否小于等于。
-
神经网络相关操作:
tf.nn.relu(x)
:ReLU(整流线性单元)激活函数。tf.nn.softmax(logits)
:计算 softmax 函数。tf.nn.conv2d(input, filter, strides, padding)
:二维卷积操作。
广播机制
广播(Broadcasting)是指在 TensorFlow 中,当两个张量在某些维度上的形状不匹配时,自动对其中一个或两个张量进行形状扩展,使它们的形状能够相互兼容,进而进行逐元素的操作。广播机制的目的是为了避免显式地复制数据,从而提高计算效率。以下是广播机制的规则:
- 如果两个张量在某个维度上的形状相等,或其中一个张量在该维度上的长度为1,则称它们在该维度上是可广播的。
- 当两个张量在某个维度上的形状不匹配时,可以通过对其中一个或两个张量在该维度上进行形状扩展,使它们的形状变得兼容,即满足广播机制的要求。
- 在广播过程中,会对形状较小的张量进行扩展,使其形状与形状较大的张量相匹配。扩展的方式是在形状较小的张量的形状前面添加维度长度为1的维度。
import tensorflow as tf
# 创建两个张量
a = tf.constant([[1, 2, 3]])
b = tf.constant([[4], [5], [6]])
# 形状不匹配,但是可以通过广播进行计算
# a 形状:(1, 3)
# b 形状:(3, 1)
# 广播后的形状:(3, 3)
result = a + b
print(result.numpy())
# 输出:
# [[5 6 7]
# [6 7 8]
# [7 8 9]]
Tensor
和NumPy相互转换
使用numpy()
将Tensor
转换成NumPy数组:
a = torch.ones(5)
b = a.numpy()
print(a, b)
a += 1
print(a, b)
b += 1
print(a, b)
使用from_numpy()
将NumPy数组转换成Tensor
:
import numpy as np
a = np.ones(5)
b = torch.from_numpy(a)
print(a, b)
a += 1
print(a, b)
b += 1
print(a, b)
此外上面提到还有一个常用的方法就是直接用torch.tensor()
将NumPy数组转换成Tensor
,需要注意的是该方法总是会进行数据拷贝,返回的Tensor
和原来的数据不再共享内存。
# 用torch.tensor()转换时不会共享内存
c = torch.tensor(a)
a += 1
print(a, c)
Tensor
on GPU
用方法to()
可以将Tensor
在CPU和GPU(需要硬件支持)之间相互移动。
# 以下代码只有在PyTorch GPU版本上才会执行
if torch.cuda.is_available():
device = torch.device("cuda") # GPU
y = torch.ones_like(x, device=device) # 直接创建一个在GPU上的Tensor
x = x.to(device) # 等价于 .to("cuda")
z = x + y
print(z)
print(z.to("cpu", torch.double)) # to()还可以同时更改数据类型
总结
TensorFlow 是一个功能强大的机器学习框架,具有广泛的应用和活跃的社区支持。在使用 TensorFlow 进行机器学习和深度学习开发时,需要掌握一些基本概念和技术,例如:
-
张量:TensorFlow 中的基本数据类型,它们是多维数组,可以表示各种类型的数据。
-
计算图:TensorFlow 的计算模型,它由一系列节点和边组成,每个节点代表一个操作,边代表张量的流动。
-
变量:TensorFlow 中的状态,它们是可以被训练的张量,可以存储模型的参数和其他状态信息。
-
会话:TensorFlow 执行计算图的环境,它可以将计算图部署到 CPU 或 GPU 上进行计算。
-
损失函数:衡量模型预测结果和实际结果之间的差异,从而指导模型的训练。
-
优化器:根据损失函数的梯度信息,更新模型参数的算法,例如随机梯度下降。
-
Dropout、Batch Normalization 等正则化技术:减少模型过拟合的方法。
-
卷积神经网络(CNN)、循环神经网络(RNN)等深度学习模型:用于处理图像、语音、自然语言等任务。
-
数据预处理技术:包括标准化、归一化、数据增强等方法,用于提高模型的鲁棒性和泛化能力。
-
广播机制:在张量形状不匹配时,自动对其中一个或两个张量进行形状扩展,使它们的形状能够相互兼容。