提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档
一、数据排序
1. sort
- 在sort中没有指出direction时,默认按递增序列排序
- 在多维张量中,排序并不是全局情况下排序,只是在最小的一个维度下排序
# 一维情况
a = tf.random.shuffle(tf.range(10))
print(a)
print(tf.sort(a))
print(tf.sort(a, direction='DESCENDING'))
# 多维情况
b = tf.random.uniform([2, 4])
print(b)
print(tf.sort(b))
print(tf.sort(b, direction='DESCENDING'))
2. argsort
返回的并不是排好序的值,而是排序好的索引
a = tf.random.shuffle(tf.range(10))
print(a)
print(tf.argsort(a))
print(tf.argsort(a, direction='DESCENDING'))
# 多维情况
b = tf.random.uniform([2, 4])
print(b)
print(tf.argsort(b))
3. top_k
返回前k个最大元素的两元组,一个是value,一个是index
c = tf.random.uniform([2, 5], maxval=20, dtype=tf.int32)
print(c)
res = tf.math.top_k(c, 3)
print(res.indices)
print(res.values)
二、数据分割
1. unstack
unstack就是stack的逆操作,把一个张量按照某一个维度切分开
代码如下(示例):
p = tf.ones([2, 4, 35, 8])
q, r = tf.unstack(p, axis=0)
print(q.shape, r.shape)
这里有一个问题:如果把axis设为3,就是说把8那个维度分隔开,还能分成两个吗?
答案是不可以,按8那个维度进行切分,就会生成8个新张量,每个张量的shape都为【2,4,35】.
这就是unstack的问题,它并不能指定分成几份。
p = tf.ones([2, 4, 35, 8])
res = tf.unstack(p, axis=3)
print(len(res))
print(res[0].shape)
并且用unstack切分后,数据的shape会自动降维,去除为1的维度
2. split
split就是在unstack的基础上进行完善,可以指定任意的切割份数,并且控制每一份的大小。
代码如下(示例):
x = tf.ones([2, 4, 35, 8])
# num_or_size_splits指定切分成几份
lips1 = tf.split(x, axis=3, num_or_size_splits=2)
lips2 = tf.split(x, axis=3, num_or_size_splits=8)
print(len(lips1))
print(lips1[0].shape)
print(len(lips2))
print(lips2[0].shape)
# 也可以确切指出在axis轴上切成每一份的大小
lips3 = tf.split(x, axis=3, num_or_size_splits=[2, 2, 4])
print(len(lips3))
print(lips3[0].shape)
print(lips3[1].shape)
print(lips3[2].shape)
即使维度的数值有1,split也不会自动降维
三、数据统计
1. 范数
- 一范数: 张量中各个元素取绝对值然后求和
- 二范数:张量中各个元素取平方然后求和最后开根号
- 无穷范数:张量中各个元素取绝对值然后取绝对值最大的那个值
tf.norm 函数用于求范数
- 设定ord=1表示求L1范数,令ord=2表示求L2范数,不给出ord时默认求L2范数
- 设定axis值表示在某一维度上进行求范数运算
代码如下(示例):
a = tf.ones([2, 2])
print(tf.norm(a))
print(tf.norm(a, ord=1))
print(tf.norm(a, ord=1, axis=1))
b = tf.ones([4, 28, 28, 3])
print(tf.norm(b))
2. 最大值最小值均值
p = tf.random.normal([4, 10])
# 求最小值
print(tf.reduce_min(p)) # 不给出axis时,默认求整个张量的最小值
print(tf.reduce_min(p, axis=1)) # 在axis=1的坐标轴上求最小值,因为有4个10列,所以会返回4个数据
# 求最大值
print(tf.reduce_max(p))
print(tf.reduce_max(p, axis=1)) # 在axis=1的坐标轴上求最大值,因为有4个10列,所以会返回4个数据
# 求均值
print(tf.reduce_mean(p))
print(tf.reduce_mean(p, axis=1)) # 在axis=1的坐标轴上求均值,因为有4个10列,所以会返回4个数据
对于求最大值和最小值,还有argmax和argmin函数用于返回目标值的位置信息。
p = tf.random.normal([4, 10])
print(tf.argmin(p)) # 不指定axis时,默认axis=0,所以会返回10个数据,每一个数据代表每一列最小元素的索引
print(tf.argmin(p, axis=1).shape) # axis=1,那么返回的数就有4个
print(tf.argmax(p))
print(tf.argmax(p, axis=1).shape)
3. 比较
tf.equal 用于比较张量间的大小关系,前提是两个张量的shape要一样。其比较的方法是:依次比较每一组对应的元素,判断是否相等,若相等记为True,若不等,记为False。
返回值就是一个对应shape的真值表。
m = tf.random.normal([4, 10])
n = tf.random.normal([4, 10])
print(tf.equal(m, n))
利用这样一种方法可以判断预测值与真实值有多少个相等,即可以算出Accuracy。一般True=1,False=0, 可以将得到的真值表从bool型转化为int型,再对整个表求和,sum值就代表了有多少个值相等。
m = tf.random.normal([4, 10])
n = tf.random.normal([4, 10])
print(tf.equal(m, n))
res = tf.equal(m, n)
sum = tf.reduce_sum(tf.cast(res, dtype=tf.int32))
print(sum)
4. 去重
tf.unique 函数返回一个张量中不重复的元素,并且都是记录新元素第一次出现的位置
x = tf.range(5)
print(tf.unique(x))
y = tf.constant([4, 2, 3, 2, 3, 6])
print(tf.unique(y))
unique的输出分为两部分:
- 第一部分就是去重后的数据
- 第二部分是操作前的数据再去重后的数据上位置的映射