昇思25天学习打卡营第3天|张量Tensor

认识张量

张量,是一个数据结构,也可以说是一个函数,它描述了标量、矢量和张量之间线性关系。这些关系包括 内积、外积、线性映射以及笛卡尔积。张量中既有大小、又有方向。张量由多个数值构成,在n维空间里,会出现 n r n^r nr 个分量,r是张量的秩或阶。

使用张量

环境配置

import numpy as np
import mindspore
from mindspore import ops
from mindspore import Tensor, CSRTensor, COOTensor

创建张量

可以通过多种方式进行张量的创建

  • 通过数据创建
data = [1, 0, 1, 0]
x_data = Tensor(data)
  • 从numpy数组创建
np_array = np.array(data)
x_np = Tensor(np_array)
  • 使用init初始化器创建
# init函数是One(),因此创建了都是1的张量
tensor1 = mindspore.Tensor(shape=(2, 2), dtype=mindspore.float32, init=One())
# init函数是Normal(),因此张量内的值遵循正态分布
tensor2 = mindspore.Tensor(shape=(2, 2), dtype=mindspore.float32, init=Normal())
  • 继承另一个张量的属性
from mindspore import ops
​# 继承全1,张量内容为 [1 1 1 1]
x_ones = ops.ones_like(x_data)# 集成全0,张量内容为 [0 0 0 0] 
x_zeros = ops.zeros_like(x_data)

张量属性

  • shape 形状:是个tuple
  • dtype 数据类型
  • itemsize 每个元素大小:tensor中每个元素占用的字节数
  • nbytes 占用字节数量:tensor占用的总字节数
  • ndim 维数:tensor的秩,len(tensor.shape)的结果,是个整数
  • size 元素个数:tensor中所有元素的个数,是个整数
  • strides 每一维步长:tensor中每一维需要的字节数,是个tuple

举例,有这样一个张量x
x = Tensor(np.array([[1, 2], [3, 4]]), mindspore.int32)
它的属性如下
x_shape: (2, 2)
x_dtype: Int32
x_itemsize: 4
x_nbytes: 16
x_ndim: 2
x_size: 4
x_strides: (8, 4)

解释一下strides为什么是(8,4)
实际上,strides指的是遍历tensor时,移动到下一个元素需要跳过的字节数。当前张量时22,类型为int32,也就是4个字节。
对于第一维(行维度),移动到下一行,就需要跨越这行所有的元素,一行有两个元素,也就是2
4 = 8字节。
对于第二维(列维度),则不需要跨越行,直接取同行的下一个元素,则只需要跨越一个元素,也就是1*4 = 4字节。

张量索引

由0开始编制,使用方法与numpy类似,支持:和…切片,支持负索引

print("Last column: {}".format(tensor[:, -1]))
# Last column: [1. 3.]

print("First column: {}".format(tensor[..., 0]))
# First column: [0. 2.]

张量运算

包括 算数、线性代数、矩阵处理(转置、标引、切片)、采样等。

output_add = x + y
output_sub = x - y
output_mul = x * y
output_div = y / x
output_mod = y % x
output_floordiv = y // x

还可以进行张量连接

data1 = Tensor(np.array([[0, 1], [2, 3]]).astype(np.float32))
data2 = Tensor(np.array([[4, 5], [6, 7]]).astype(np.float32))
output = ops.concat((data1, data2), axis=0)
# [[0. 1.]
# [2. 3.]
# [4. 5.]
# [6. 7.]]
#shape:
# (4, 2)

以及张量合并

output = ops.stoutput = ops.stack([data1, data2])
# [[[0. 1.]
#   [2. 3.]]
# 
#  [[4. 5.]
#   [6. 7.]]]
# shape:
#  (2, 2, 2)

tensor和numpy互转

# tensor转numpy
t = Tensor([1., 1., 1., 1., 1.])
n = t.asnumpy()
# numpy转tensor
n = np.ones(5)
t = Tensor.from_numpy(n)

稀疏张量

稀疏是稠密的反义词,稠密就是张量里都是元素,稀疏就是张量里零星几个元素,其他都是0.
如果使用普通张量来存储这类向量会造成不必要的计算、存储和通讯浪费。MindSpore有CSRTensor和COOTensor、RowTensor三种稀疏矩张量。

稀疏张量的表达形式是<indices:Tensor, values:Tensor, shape:Tensor>。其中,indices表示非零下标元素, values表示非零元素的值,shape表示的是被压缩的稀疏张量的形状。

CSRTensor

全称Compressed Sparse Row。s。各参数含义为:

  • indptr: 一维整数张量, 表示稀疏数据每一行的非零元素在values中的起始位置和终止位置。
  • indices: 一维整数张量,表示稀疏张量非零元素在列中的位置。长度等于values.
  • values: 一维张量,非零元素的值
  • shape: 表示被压缩的稀疏张量的形状,数据类型为Tuple
indptr = Tensor([0, 1, 2])
indices = Tensor([0, 1])
values = Tensor([1, 2], dtype=mindspore.float32)
shape = (2, 4)

# Make a CSRTensor
csr_tensor = CSRTensor(indptr, indices, values, shape)

要特别说一下,indptr一共三个值,表示第0行的非零元素从索引0开始,第1行的非零元素从索引1开始,而且这个数组的长度比实际的行数多一个,最后一个元素用于表示非零元素的总数。最后得到的张量这样的。

行0: [1, 0, 0, 0]
行1: [0, 2, 0, 0]

COOTensor

全称 Coordinate Format,各参数含义如下:

indices: 二维张量,每行代表非零元素下标。形状:[N, ndims]。
values: 一维张量,非零元素的值。形状:[N]。
shape: 稀疏张量的形状

indices = Tensor([[0, 1], [1, 2]], dtype=mindspore.int32)
values = Tensor([1, 2], dtype=mindspore.float32)
shape = (3, 4)

# Make a COOTensor
coo_tensor = COOTensor(indices, values, shape)

indices = [[0, 1], [1, 2]]意味着有两个非零元素,分别位于坐标(0,1)和(1,2)。得到的张量如下
0 1 0 0
0 0 2 0
0 0 0 0

总结

今天学习了张量的基本概念,如何创建张量、张量属性、张量计算以及稀疏张量的创建。

打卡凭证

在这里插入图片描述

  • 21
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值