当前位置:网站首页>3.张量运算
3.张量运算
2022-08-03 04:05:00 【好名字能更容易让朋友记住】
张量运算
深度神经网络学到的所有变换也都可以简化为数值数据张量上的一些张量运算(tensor operation)
对于叠加Dense层来构建网络。Keras层的示例如下所示。
keras.layers.Dense(512, activation=‘relu’)
这个层可以理解为一个函数,输入一个2D张量,返回另一个2D张量,即输入张量的新表示。具体而言,如以下这个函数表示
output = relu(dot(W, input) + b)
其中W是一个2D张量,b是一个向量,二者都是该层的属性。拆开来看,这里有三个张量运算:
- 输入张量和张量W之间的点积运算(dot)
- 得到的2D张量与向量b之间的加法运算(+)
- 最后的relu运算。relu(x)是max(x,0)
逐元素运算
relu 运算和加分都是逐元素(element-wise)的运算,即运算独立地应用于张量中的每个元素,也就是说,这些运算非常适合大规模并行实现(向量化实现)
以下代码是对逐元素 relu 运算的简单实现
def navie_relu(x): assert len(x.shape) == 2 # assert 断言 以上语句的意思为如果 len(x.shape)==2即表示True,则正常运行,反之会报错。 x = x.copy() # 避免覆盖输入张量 for i in range(x.shape[0]): for j in range(x.shape[1]): x[i, j] = max(x[o, j], 0) return x
对于加法采用同样的实现方法。
def navie_add(x, y): assert len(x.shape) == 2 assert x.shape == y.shape # 保证 x 和 y 是Numpy的2D张量 x = x.copy() for i in range(x.shape[0]): for j in range(x.shape[1]): x[i, j] += y[i, j] return
在Numpy中可以直接进行下列逐元素运算,速度非常快
import numpy as np # 逐元素相加 z = x + y # 逐元素的relu z = np.maxinum(z, 0.)
广播
对于以上的 navie_add 的简单实现仅支持两个形状相同的2D张量相加。如果将两个形状不同的张量相加。较小的张量会被广播,以匹配较大张量的形状。广播包括以下两步:
- 将较小的张量添加轴(叫做广播轴),使其ndim与较大的张量相同。
- 将较小的张量沿着新轴重复,使其形状与较大的张量相同。
举例:
假设X的形状是(32,10),y的形状是(10,)。首先,我们给y添加一个空的第一个轴,这样y的形状变为(1,10)。然后,我们将y沿着新轴重复32次,这样得到张量Y的形状为(32,10),并且Y[i, :] == y for i in range(0,32)。此时二者可以相加。def navie_add_matrix_and_vector(x, y): assert len(x.shape) == 2 assert len(y.shape) == 1 assert x.shape[1] == y.shape[0] x = x.copy() for i in range(x.shape[0]): for j in range(x.shape[1]): x[i, j] += y[j] return x
如果一个张量的形状是(a,b,… n,n+1, … ,m),另一个张量为(n,n+1,… m),那么你可以利用广播对他们做两个张量之间的逐元素运算。广播操作会自动应用于a到n-1的轴。
# 利用广播将逐元素的maximum运算应用于两个形状不同的张量 import numpy as np # 形状为(64,3,32,10)的随机张量、 x = np.random.random((64, 3, 32, 10)) # 形状为(64,10)的随机张量。 y = np.random.random((32, 10)) # 输出z的形状是(64,3,32,10),与x相同。 z = np.maximum(x, y)
张量点积
点积运算,也叫做张量积(tensor product,不要与逐元素的乘积弄混)
在Numpy、Keras、Theano和TensorFlow中,都是用 * 实现逐元素乘积。TensorFlow中的点积使用了不同的语法,但在Numpy和Keras中,都是用标准的dot运算符来实现点积。
import numpy as np z = np.dot(x, y) # 数学符号中的点( . )表示点击运算。 z=x.y
从数学的角度来看,两个向量 x 和 y 的点积。其运算结果如下:
def navie_vector_dot(x, y): # 表示二者为向量 assert len(x.shape) == 1 assert len(y.shape) == 1 # 表示长度相同 assert x.shape[0] == y.shape[0] z = 0. for i in range(x.shape[0]): z += x[i] * y[i] # 返回值为一个标量 return z
矩阵x和一个向量y做点积:
import numpy as np def naive_matrix_vector_dot(x, y): # x 是一个Numpy矩阵 # y 是一个Numpy向量 assert len(x.shape) == 2 assert len(y.shape) == 1 # x的第1维和y的第0维大小必须相同 assert x.shape[1] == y.shape[0] z = np.zeros(x.shape[0]) for i in range(x.shape[0]): for j in range(x.shape[1]): z[i] += x[i, j] * y[j] return z
举例:
import numpy as np x = np.array([[1,2,3],[4,5,6]]) y = np.array([1,2,3]) z = navie_matrix_vector_dot(x,y) z # z = array([14., 32.]) # 即 z = [1×1 + 2×2 + 3×3 , 4×1 + 5×2 + 6×3]
通过以上两个函数进行结合
def mavie_matrix_vector_dot(x,y): z = np.zeros(x.shape[0]) for i in range(x.shape[0]): z[i] = naive_vector_dot(x[i, :], y) # x[i, :]表示x的第i个轴的所有元素 return z
进行推广,若两个矩阵进行点积,若矩阵x和y,当且仅当 x.shape[1] == y.shape[0] 时,二者可以进行点积。得到的结果为一个形状为**(x.shape[0],y.shape[1])**的矩阵。
def navie_matrix_dot(x, y): assert len(x.shape) == 2 assert len(y.shape) == 2 # x的第1维与y的第0维大小必须相同 # 即x的列数与y的行数相等 assert x.shape[1] == y.shape[0] z = np.zeros((x.shape[0], y.shape[1])) for i in range(x.shape[0]): for j in range(y.shape[1]): # 遍历x的所有行 row_x = x[i, :] # 遍历y的所有列 column_y = y[:, j] # x的行依次与y的列相乘 z[i, j] = navie_vector_dot(row_x, column_y) return z
综上所述:
两个矩阵相乘需要的要求为矩阵x的列于矩阵y的行相等,再将矩阵x的行依次与矩阵y的列想称再相加。得到一个以矩阵x的行为行,矩阵y的列为列的新矩阵。 一般来说,可以对更高维的张量做点积,只要其形状匹配遵循与前面2D张量相同的原则:
(a, b , c ,d) . (d,) -> (a, b, c)
(a, b , c ,d) . (d, e) -> (a, b, c, e)
以此类推。
张量变形
改变张量的行和列,以得到想要的形状,变形后的张量的元素总个数与初始张量相同。
举例:
x = np.array([[0., 1.], [2., 3.], [4., 5.]]) print(x.shape) # (3, 2) x = reshape((6, 1)) x # array([[ 0.], # 1.], # 2.], # 3.], # 4.], # 5.]]) x = x.reshape((2, 3)) x # array([[ 0., 1., 2.],[ 3., 4., 5.]])
最经常遇到的一种特殊的张量变形是转置。对矩阵做转置是指将行和列互换,使x[i, :]变为x[:, i]。
x = np.zeros((300,20)) x = np.transpose(x) print(x.shape)
边栏推荐
猜你喜欢
StarRocks 7 月社区动态
汇编题答案
C# WPF设备监控软件(经典)-上篇
多线程使用哈希表
银微转债,洁特转债上市价格预测
Shenzhen Offline Registration|StarRocks on AWS: How to conduct rapid and unified analysis of real-time data warehouses
工程制图第九章作业
Chapter 8 Character Input Output and Input Validation
数据库性能系列之索引(中)
t conditional judgment statement and if loop
随机推荐
计组错题集
9 椭圆曲线密码体制
OpenFOAM提取等职面并计算面积
2022 Henan Mengxin League Game (4): Zhengzhou University of Light Industry E - Sleep Well
瑞鹄转债上市价格预测
汇编书摘抄
Compose the displacement of the view
js Fetch返回数据res.json()报错问题
数字3d虚拟交互展厅顺应时代发展需求和趋势
那些让电子工程师崩溃瞬间,你经历了几个呢?
Assembly answers
利用索引机制进行绕过
Test drive: project management module - curd development project
高等代数_证明_矩阵乘以自身的转置的特征值不小于0
工程制图-齿轮
【笔记】混淆矩阵和ROC曲线
How many moments have you experienced the collapse of electronic engineers?
2022河南萌新联赛第(四)场:郑州轻工业大学 G - 迷宫
mysql bool盲注
js的组成及js样式