神經網絡學習小記錄41——一些常用的tensorflow操作彙總

學習前言

Keras以tensorflow作爲後端,在Keras網絡構建中需要對特徵層進行操作的話,需要用到很多tf函數,這些tf函數的執行過程比較迷糊,需要學習一下。
在這裏插入圖片描述

特徵層or圖像處理

1、tf.image.crop_and_resize

這是在對圖像、特徵層處理經常用到的函數,可以對特徵層或者圖像進行裁剪,裁剪之後再進行resize。

tf.image.crop_and_resize(
    image,
    boxes,
    box_ind,
    crop_size,
    method='bilinear',
    extrapolation_value=0,
    name=None
)

參數:

  • image:一個Tensor,必須是下列類型之一:uint8, uint16, int8, int16, int32, int64, half, float32, float64, 一個形狀爲[batch, image_height, image_width, depth]的四維張量,image_height和image_width需要爲正值.
  • boxes:一個類型爲float32的Tensor,是形狀爲[num_boxes, 4]的二維張量。張量的第i行指定box_ind[i]圖像中框的座標,並且在標準化座標中指定[y1, x1, y2, x2],四個座標均是標準歸一化後的結果;標準化的座標值y被映射到圖像座標y * (image_height - 1)處,從而標準化圖像高度的[0, 1]間隔被映射到[0, image_height - 1]的圖像高度座標中。我們允許y1>y2,在這種情況下,採樣的裁剪是原始圖像的上下翻轉版本,寬度維度的處理方式類似。[0,1]範圍之外的標準化座標是允許的,在這種情況下,我們使用extrapolation_value外推輸入圖像值
  • box_ind:一個int32類型的Tensor;形狀爲[num_boxes]的1維張量,在[0, batch)中具有int32值,該box_ind[i]值指定第i個方框要引用的圖像。
  • crop_size:一個int32類型的Tensor;一個2個元素的一維張量,size = [crop_height, crop_width]。所有裁剪的圖像修補程序都調整爲此大小.圖像內容的寬高比不被保留;crop_height和crop_width需要爲正值。
  • method:可選的string,其來自:“bilinear”;默認爲"bilinear";指定插值方法的字符串.現在只支持“雙線性(bilinear)”.
  • extrapolation_value:可選的float,默認爲0,用於推斷的值(如果適用). name:操作的名稱(可選).

返回值:
tf.image.crop_and_resize函數返回一個類型爲float32的Tensor. 形狀爲[num_boxes, ,crop_height, crop_width, depth]

測試代碼爲:

import tensorflow as tf
from PIL import Image
import numpy as np
img = np.array(Image.open("img/street.jpg"))
shape = img.shape
img = img.reshape([1,shape[0], shape[1], shape[2]])
a = tf.image.crop_and_resize(img,[[0.5,0.6,0.9,0.8],[0.2,0.6,1.3,0.9]],box_ind=[0,0],crop_size=(100,100))
sess = tf.Session()
b = a.eval(session = sess)
Image.fromarray(np.uint8(b[0])).show()

輸出爲:
在這裏插入圖片描述

(2, 100, 100, 3)

2、tf.image.resize_images

這是在對圖像、特徵層處理經常用到的函數,可以對特徵層或者圖像resize。

tf.image.resize_images(
    images,
    size,
    method=ResizeMethod.BILINEAR,
    align_corners=False
)

使用指定的method調整images爲size。
調整大小的圖像將失真,如果他們的原始縱橫比與size不一樣。

  • images:形狀爲[batch, height, width, channels]的4-D張量或形狀爲[height, width, channels]的3-D張量。
  • size:2個元素(new_height, new_width)的1維int32張量,表示圖像的新大小。
  • method:ResizeMethod,默認爲ResizeMethod.BILINEAR。
  • align_corners:布爾型,如果爲True,則輸入和輸出張量的4個拐角像素的中心對齊,並且保留角落像素處的值;默認爲False。

如果images是四維,則返回一個形狀爲[batch, new_height, new_width, channels]的四維浮動張量;如果images是三維,則返回一個形狀爲[new_height, new_width, channels]的三維浮動張量.

測試代碼爲:

import tensorflow as tf
from PIL import Image
import numpy as np
img = np.array(Image.open("img/street.jpg"))
shape = img.shape
img = img.reshape([1,shape[0], shape[1], shape[2]])
a = tf.image.crop_and_resize(img,[[0.5,0.6,0.9,0.8],[0.2,0.6,1.3,0.9]],box_ind=[0,0],crop_size=(100,100))
sess = tf.Session()
b = a.eval(session = sess)
Image.fromarray(np.uint8(b[0])).show()

輸出爲:
在這裏插入圖片描述

(1, 100, 100, 3)

3、tf.transpose

可以對輸入進行轉置。

tf.transpose(
    a,
    perm=None,
    name='transpose',
    conjugate=False
)
  • a:一個 Tensor。
  • perm:a 的維數的排列。
  • name:操作的名稱(可選)。

tf.transpose函數返回一個轉置 Tensor。

測試代碼爲:

import tensorflow as tf
import numpy as np
sess=tf.Session()

a = tf.constant([[1, 2, 3], [4, 5, 6]])

a = tf.transpose(a, perm=[1, 0])    # [[1, 4]
                                    #  [2, 5]
                                    #  [3, 6]]


b = tf.constant([[[ 1,  2,  3],
                  [ 4,  5,  6]],
                 [[ 7,  8,  9],
                  [10, 11, 12]]])

b = tf.transpose(b, perm=[0, 2, 1])


c = tf.constant([[[ 1,  2,  3],
                  [ 4,  5,  6]],
                 [[ 7,  8,  9],
                  [10, 11, 12]]])

c = tf.transpose(c, perm=[2, 0, 1])

print(sess.run(a))
print(sess.run(b))
print(sess.run(c))

輸出爲:

[[1 4]
 [2 5]
 [3 6]]
[[[ 1  4]
  [ 2  5]
  [ 3  6]]

 [[ 7 10]
  [ 8 11]
  [ 9 12]]]
[[[ 1  4]
  [ 7 10]]

 [[ 2  5]
  [ 8 11]]

 [[ 3  6]
  [ 9 12]]]

獲得特定位置的內容

1、tf.gather

這是在對某些內容進行篩選的時候經常用到的函數,可以獲得某個切片的內容。

tf.gather(
    params,
    indices,
    validate_indices=None,
    name=None,
    axis=0
)
  • params:一個張量,這個張量是用來收集數值的.該張量的秩必須至少是 axis + 1。
  • indices:一個張量.必須是以下類型之一:int32,int64.索引張量必須在 [0, params.shape[axis]) 範圍內。
  • axis:一個張量.必須是以下類型之一:int32,int64。在參數軸從中收集索引。默認爲第一個維度.支持負索引。
  • name:操作的名稱(可選)。

測試代碼爲:

import tensorflow as tf
 
a = tf.Variable([[1,2,3,4,5], [6,7,8,9,10], [11,12,13,14,15]])
index_a = tf.Variable([0,1,2,3])
 
b = tf.Variable([1,2,3,4,5,6,7,8,9,10])
index_b = tf.Variable([2,4,6,8])
 
with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())
    print(sess.run(tf.gather(a, index_a)))
    print(sess.run(tf.gather(a, index_a,axis = 1)))
    print(sess.run(tf.gather(b, index_b)))

輸出爲:

[[ 1  2  3  4  5]
 [ 6  7  8  9 10]
 [11 12 13 14 15]
 [ 0  0  0  0  0]]
[[ 1  2  3  4]
 [ 6  7  8  9]
 [11 12 13 14]]
[3 5 7 9]

2、tf.gather_nd

這是在對某些內容進行篩選的時候經常用到的函數,可以獲得特定位置的內容。

tf.gather_nd(
    params,
    indices,
    name=None
)
  • params:張量,這個張量是用來收集數值的。
  • indices:張量,必須是以下類型之一:int32,int64;索引張量。
  • name:操作的名稱(可選)。

測試代碼爲:

import tensorflow as tf
 
a = tf.Variable([[1,2,3,4,5], [6,7,8,9,10], [11,12,13,14,15]])
index_a = tf.Variable([[0,1],[0,0],[1,3],[2,4]])

b = tf.Variable([[[1,2,3],[4,5,6]], [[6,7,8],[9,10,11]], [[11,12,13],[14,15,16]]])
index_b = tf.Variable([[0,1],[0,0],[1,1],[2,2]])
index_c = tf.Variable([[0,1,1],[0,0,0],[1,1,1],[2,2,2]])
 
with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())
    print(sess.run(tf.gather_nd(a, index_a)))
    print(sess.run(tf.gather_nd(b, index_b)))
    print(sess.run(tf.gather_nd(b, index_c)))

輸出爲:

[ 2  1  9 15]
[[ 4  5  6]
 [ 1  2  3]
 [ 9 10 11]
 [ 0  0  0]]
[ 5  1 10  0]

3、tf.where

給定一個表達式,判斷哪些位置符合這個表達式。

tf.where(
    condition,
    x=None,
    y=None,
    name=None
)

根據condition返回x或y中的元素。

如果x和y都爲None,則該操作將返回condition中true元素的座標,座標以二維張量返回,其中第一維(行)表示真實元素的數量,第二維(列)表示真實元素的座標。

如果兩者都不是None。則x和y必須具有相同的形狀。如果x和y是標量,則condition張量必須是標量,如果x和y是更高級別的矢量,則condition必須是大小與x的第一維度相匹配的矢量,或者必須具有與x相同的形狀。

condition張量作爲一個可以選擇的掩碼(mask),它根據每個元素的值來判斷輸出中的相應元素/行是否應從 x (如果爲 true) 或 y (如果爲 false)中選擇。

如果condition是向量,則x和y是更高級別的矩陣,那麼它選擇從x和y複製哪個行(外部維度)。如果condition與x和y具有相同的形狀,那麼它將選擇從x和y複製哪個元素。

測試代碼爲:

import tensorflow as tf
import numpy as np
sess=tf.Session()

#-------------------#
#   用法1:
#   x,y沒值的時候
#-------------------#
a=[[[True, False],
    [True, False]],
   [[False, True],
    [False, True]],
   [[False, False],
    [False, True]]]
print(sess.run(tf.where(a)))
#-------------------#
#   用法2:
#   x,y有值的時候
#-------------------#
a=np.array([[1,0,0],[0,1,1]])
a1=np.array([[3,2,3],[4,5,6]])

print(sess.run(tf.equal(a,1)))
print(sess.run(tf.where(tf.equal(a,1),a,a1)))

輸出爲:

[[0 0 0]
 [0 1 0]
 [1 0 1]
 [1 1 1]
 [2 1 1]]
[[ True False False]
 [False  True  True]]
[[1 2 3]
 [4 1 1]]

矩陣操作

1、tf.cast

tf.cast(
    x,
    dtype,
    name=None
)

tf.cast()函數的作用是執行 tensorflow 中張量數據類型轉換,比如讀入的圖片如果是int8類型的,一般在要在訓練前把圖像的數據格式轉換爲float32。

  • x:待轉換的數據(張量)
  • dtype:目標數據類型
  • name:可選參數,定義操作的名稱

測試代碼爲:

import tensorflow as tf
import numpy as np

t1 = tf.Variable([1,2,3,4,5])
t2 = tf.cast(t1,dtype=tf.float32)

with tf.Session() as sess:
    print('t1: {}'.format(t1))
    print('t2: {}'.format(t2))
    sess.run(tf.global_variables_initializer())
    sess.run(t2)
    print(t2.eval())

輸出爲:

[1. 2. 3. 4. 5.]

2、tf.stack

tf.stack(
    values,
    axis=0,
    name='stack'
)

將秩爲 R 的張量列表堆疊成一個秩爲 (R+1) 的張量.

  • values:具有相同形狀和類型的 Tensor 對象列表.
  • axis:一個 int,要一起堆疊的軸,默認爲第一維,負值環繞,所以有效範圍是[-(R+1), R+1)
  • name:此操作的名稱(可選)。

測試代碼爲:

import tensorflow as tf
import numpy as np

x = tf.constant([1, 4])
y = tf.constant([2, 5])
z = tf.constant([3, 6])

s0 = tf.stack([x, y, z])  # [[1, 4], [2, 5], [3, 6]] (Pack along first dim.)
s1 = tf.stack([x, y, z], axis=1)  # [[1, 2, 3], [4, 5, 6]]

with tf.Session() as sess:
    print(sess.run(s0))
    print(sess.run(s1))

輸出爲:

[[1 4]
 [2 5]
 [3 6]]
[[1 2 3]
 [4 5 6]]

3、tf.concat

用於對張量進行拼接:

tf.concat(
	[tensor1, tensor2, tensor3,...], 
	axis
)

測試代碼:

import tensorflow as tf
import numpy as np

x = tf.constant([1, 4])
y = tf.constant([2, 5])
z = tf.constant([3, 6])

s0 = tf.concat([x, y, z], axis=0)  # [[1, 4], [2, 5], [3, 6]] (Pack along first dim.)


x = tf.constant([[1], 
                 [4]])
y = tf.constant([[2], 
                 [5]])
z = tf.constant([[3], 
                 [6]])

s1 = tf.concat([x, y, z], axis=0) 
s2 = tf.concat([x, y, z], axis=1) 

with tf.Session() as sess:
    print(sess.run(s0))
    print(sess.run(s1))
    print(sess.run(s2))

輸出爲:

[1 4 2 5 3 6]
[[1]
 [4]
 [2]
 [5]
 [3]
 [6]]
[[1 2 3]
 [4 5 6]]

4、tf.reduce_max

用於求取某個維度最大值:

tf.reduce_max(
    input_tensor,
    axis=None,
    keep_dims=False,
    name=None,
    reduction_indices=None
)

計算一個張量的各個維度上元素的最大值.
按照axis給定的維度減少input_tensor。除非 keep_dims 是true,否則張量的秩將在axis的每個條目中減少1。如果keep_dims爲true,則減小的維度將保留爲長度1。

  • input_tensor:要使用的張量。。
  • axis:要減小的尺寸。如果爲,None(默認),則減少所有維度.必須在[-rank(input_tensor), rank(input_tensor))範圍內。
  • keep_dims:如果爲true,則保留長度爲1的減少維度。
  • name:操作的名稱(可選)。
  • reduction_indices:axis的廢棄的名稱。

測試代碼:

import tensorflow as tf
import numpy as np

a=np.array([[1, 2],
            [5, 3],
            [2, 6]])

b = tf.Variable(a)
with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())
    print(sess.run(tf.reduce_max(b)))
    print(sess.run(tf.reduce_max(b, axis=1, keepdims=False)))
    print(sess.run(tf.reduce_max(b, axis=1, keepdims=True)))
    print(sess.run(tf.reduce_max(b, axis=0, keepdims=True)))

輸出爲:

6
[2 5 6]
[[2]
 [5]
 [6]]
[[5 6]]
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章