RSVP สำหรับกิจกรรม TensorFlow Everywhere ในพื้นที่ของคุณวันนี้!
หน้านี้ได้รับการแปลโดย Cloud Translation API
Switch to English

รู้เบื้องต้นเกี่ยวกับ Tensors

ดูใน TensorFlow.org เรียกใช้ใน Google Colab ดูแหล่งที่มาบน GitHub ดาวน์โหลดสมุดบันทึก
import tensorflow as tf
import numpy as np

Tensors คืออาร์เรย์หลายมิติที่มีประเภทสม่ำเสมอ (เรียกว่า dtype ) คุณสามารถดู dtypes ที่รองรับทั้งหมดได้ที่tf.dtypes.DType

หากคุณคุ้นเคยกับ NumPy แล้วเทนเซอร์จะ (ชนิด) เหมือน np.arrays

เทนเซอร์ทั้งหมดไม่เปลี่ยนรูปเช่นหมายเลข Python และสตริง: คุณไม่สามารถอัปเดตเนื้อหาของเทนเซอร์ได้เพียงสร้างใหม่

พื้นฐาน

มาสร้างเทนเซอร์พื้นฐานกัน

นี่คือเทนเซอร์ "สเกลาร์" หรือ "อันดับ-0" สเกลาร์ประกอบด้วยค่าเดียวและไม่มี "แกน"

# This will be an int32 tensor by default; see "dtypes" below.
rank_0_tensor = tf.constant(4)
print(rank_0_tensor)
tf.Tensor(4, shape=(), dtype=int32)

เทนเซอร์ "vector" หรือ "rank-1" ก็เหมือนรายการค่า เวกเตอร์มีแกนเดียว:

# Let's make this a float tensor.
rank_1_tensor = tf.constant([2.0, 3.0, 4.0])
print(rank_1_tensor)
tf.Tensor([2. 3. 4.], shape=(3,), dtype=float32)

"เมทริกซ์" หรือ "อันดับ -2" เทนเซอร์มีสองแกน:

# If you want to be specific, you can set the dtype (see below) at creation time
rank_2_tensor = tf.constant([[1, 2],
                             [3, 4],
                             [5, 6]], dtype=tf.float16)
print(rank_2_tensor)
tf.Tensor(
[[1. 2.]
 [3. 4.]
 [5. 6.]], shape=(3, 2), dtype=float16)

สเกลาร์รูปร่าง: [] เวกเตอร์รูปร่าง: [3] เมทริกซ์รูปร่าง: [3, 2]
สเกลาร์หมายเลข 4บรรทัดที่มี 3 ส่วนแต่ละส่วนมีตัวเลขตาราง 3x2 โดยแต่ละเซลล์จะมีตัวเลข

เทนเซอร์อาจมีแกนมากขึ้น นี่คือเทนเซอร์ที่มีสามแกน:

# There can be an arbitrary number of
# axes (sometimes called "dimensions")
rank_3_tensor = tf.constant([
  [[0, 1, 2, 3, 4],
   [5, 6, 7, 8, 9]],
  [[10, 11, 12, 13, 14],
   [15, 16, 17, 18, 19]],
  [[20, 21, 22, 23, 24],
   [25, 26, 27, 28, 29]],])

print(rank_3_tensor)
tf.Tensor(
[[[ 0  1  2  3  4]
  [ 5  6  7  8  9]]

 [[10 11 12 13 14]
  [15 16 17 18 19]]

 [[20 21 22 23 24]
  [25 26 27 28 29]]], shape=(3, 2, 5), dtype=int32)

มีหลายวิธีที่คุณอาจเห็นภาพของเทนเซอร์ที่มีมากกว่าสองแกน

เทนเซอร์ 3 แกนรูปร่าง: [3, 2, 5]

คุณสามารถแปลงเทนเซอร์เป็นอาร์เรย์ NumPy ได้โดยใช้ np.array หรือเมธอด tensor.numpy :

np.array(rank_2_tensor)
array([[1., 2.],
       [3., 4.],
       [5., 6.]], dtype=float16)
rank_2_tensor.numpy()
array([[1., 2.],
       [3., 4.],
       [5., 6.]], dtype=float16)

เทนเซอร์มักประกอบด้วยโฟลตและอินเทอร์ แต่มีอีกหลายประเภท ได้แก่ :

  • จำนวนเชิงซ้อน
  • สตริง

คลาส tf.Tensor ฐานกำหนดให้เทนเซอร์เป็น "สี่เหลี่ยม" - นั่นคือตามแต่ละแกนทุกองค์ประกอบมีขนาดเท่ากัน อย่างไรก็ตามมีเทนเซอร์ชนิดพิเศษที่สามารถจัดการกับรูปร่างที่แตกต่างกันได้:

  • Ragged Tensors (ดู RaggedTensor ด้านล่าง)
  • เทนเซอร์แบบเบาบาง (ดู SparseTensor ด้านล่าง)

คุณสามารถทำคณิตศาสตร์พื้นฐานเกี่ยวกับเทนเซอร์ได้รวมถึงการบวกการคูณตามองค์ประกอบและการคูณเมทริกซ์

a = tf.constant([[1, 2],
                 [3, 4]])
b = tf.constant([[1, 1],
                 [1, 1]]) # Could have also said `tf.ones([2,2])`

print(tf.add(a, b), "\n")
print(tf.multiply(a, b), "\n")
print(tf.matmul(a, b), "\n")
tf.Tensor(
[[2 3]
 [4 5]], shape=(2, 2), dtype=int32) 

tf.Tensor(
[[1 2]
 [3 4]], shape=(2, 2), dtype=int32) 

tf.Tensor(
[[3 3]
 [7 7]], shape=(2, 2), dtype=int32) 


print(a + b, "\n") # element-wise addition
print(a * b, "\n") # element-wise multiplication
print(a @ b, "\n") # matrix multiplication
tf.Tensor(
[[2 3]
 [4 5]], shape=(2, 2), dtype=int32) 

tf.Tensor(
[[1 2]
 [3 4]], shape=(2, 2), dtype=int32) 

tf.Tensor(
[[3 3]
 [7 7]], shape=(2, 2), dtype=int32) 


Tensors ใช้ในการดำเนินการทุกประเภท (ops)

c = tf.constant([[4.0, 5.0], [10.0, 1.0]])

# Find the largest value
print(tf.reduce_max(c))
# Find the index of the largest value
print(tf.argmax(c))
# Compute the softmax
print(tf.nn.softmax(c))
tf.Tensor(10.0, shape=(), dtype=float32)
tf.Tensor([1 0], shape=(2,), dtype=int64)
tf.Tensor(
[[2.6894143e-01 7.3105854e-01]
 [9.9987662e-01 1.2339458e-04]], shape=(2, 2), dtype=float32)

เกี่ยวกับรูปร่าง

เทนเซอร์มีรูปร่าง คำศัพท์บางคำ:

  • รูปร่าง : ความยาว (จำนวนองค์ประกอบ) ของแต่ละแกนของเทนเซอร์
  • อันดับ : จำนวนแกนเทนเซอร์ สเกลาร์มีอันดับ 0 เวกเตอร์มีอันดับ 1 เมทริกซ์คืออันดับ 2
  • แกน หรือ มิติ : มิติเฉพาะของเทนเซอร์
  • ขนาด : จำนวนรายการทั้งหมดในเทนเซอร์เวกเตอร์รูปร่างผลิตภัณฑ์

Tensors และ tf.TensorShape วัตถุ tf.TensorShape มีคุณสมบัติที่สะดวกในการเข้าถึงสิ่งเหล่านี้:

rank_4_tensor = tf.zeros([3, 2, 4, 5])
เทนเซอร์อันดับ -4 รูปร่าง: [3, 2, 4, 5]
รูปร่างเทนเซอร์ก็เหมือนเวกเตอร์เทนเซอร์ 4 แกน
print("Type of every element:", rank_4_tensor.dtype)
print("Number of axes:", rank_4_tensor.ndim)
print("Shape of tensor:", rank_4_tensor.shape)
print("Elements along axis 0 of tensor:", rank_4_tensor.shape[0])
print("Elements along the last axis of tensor:", rank_4_tensor.shape[-1])
print("Total number of elements (3*2*4*5): ", tf.size(rank_4_tensor).numpy())
Type of every element: <dtype: 'float32'>
Number of axes: 4
Shape of tensor: (3, 2, 4, 5)
Elements along axis 0 of tensor: 3
Elements along the last axis of tensor: 5
Total number of elements (3*2*4*5):  120

ในขณะที่ดัชนีมักอ้างถึงแกน แต่คุณควรติดตามความหมายของแต่ละแกนอยู่เสมอ มักจะเรียงลำดับแกนจากส่วนกลางไปยังท้องถิ่น: แกนแบตช์ก่อนตามด้วยมิติข้อมูลเชิงพื้นที่และคุณลักษณะสำหรับแต่ละตำแหน่งสุดท้าย ด้วยวิธีนี้คุณสมบัติเวกเตอร์เป็นพื้นที่ที่อยู่ติดกัน

ลำดับแกนทั่วไป
ติดตามว่าแต่ละแกนเป็นอย่างไร ตัวเทนเซอร์ 4 แกนอาจเป็น: แบทช์, ความกว้าง, ความสูง, คุณสมบัติ

การจัดทำดัชนี

การจัดทำดัชนีแกนเดียว

TensorFlow เป็นไปตามกฎการจัดทำดัชนี Python มาตรฐานคล้ายกับการ สร้างดัชนีรายการหรือสตริงใน Python และกฎพื้นฐานสำหรับการจัดทำดัชนี NumPy

  • ดัชนีเริ่มต้นที่ 0
  • ดัชนีเชิงลบจะนับถอยหลังจากจุดสิ้นสุด
  • เครื่องหมายทวิภาค : ใช้สำหรับชิ้นส่วน: start:stop:step
rank_1_tensor = tf.constant([0, 1, 1, 2, 3, 5, 8, 13, 21, 34])
print(rank_1_tensor.numpy())
[ 0  1  1  2  3  5  8 13 21 34]

การสร้างดัชนีด้วยสเกลาร์จะลบแกน:

print("First:", rank_1_tensor[0].numpy())
print("Second:", rank_1_tensor[1].numpy())
print("Last:", rank_1_tensor[-1].numpy())
First: 0
Second: 1
Last: 34

การสร้างดัชนีด้วย a : slice ทำให้แกน:

print("Everything:", rank_1_tensor[:].numpy())
print("Before 4:", rank_1_tensor[:4].numpy())
print("From 4 to the end:", rank_1_tensor[4:].numpy())
print("From 2, before 7:", rank_1_tensor[2:7].numpy())
print("Every other item:", rank_1_tensor[::2].numpy())
print("Reversed:", rank_1_tensor[::-1].numpy())
Everything: [ 0  1  1  2  3  5  8 13 21 34]
Before 4: [0 1 1 2]
From 4 to the end: [ 3  5  8 13 21 34]
From 2, before 7: [1 2 3 5 8]
Every other item: [ 0  1  3  8 21]
Reversed: [34 21 13  8  5  3  2  1  1  0]

การจัดทำดัชนีหลายแกน

ตัวนับอันดับที่สูงกว่าจะถูกจัดทำดัชนีโดยการส่งผ่านหลายดัชนี

กฎเดียวกันกับในกรณีแกนเดียวใช้กับแต่ละแกนโดยอิสระ

print(rank_2_tensor.numpy())
[[1. 2.]
 [3. 4.]
 [5. 6.]]

การส่งผ่านจำนวนเต็มสำหรับแต่ละดัชนีผลลัพธ์คือสเกลาร์

# Pull out a single value from a 2-rank tensor
print(rank_2_tensor[1, 1].numpy())
4.0

คุณสามารถจัดทำดัชนีโดยใช้การรวมกันของจำนวนเต็มและส่วนต่างๆ:

# Get row and column tensors
print("Second row:", rank_2_tensor[1, :].numpy())
print("Second column:", rank_2_tensor[:, 1].numpy())
print("Last row:", rank_2_tensor[-1, :].numpy())
print("First item in last column:", rank_2_tensor[0, -1].numpy())
print("Skip the first row:")
print(rank_2_tensor[1:, :].numpy(), "\n")
Second row: [3. 4.]
Second column: [2. 4. 6.]
Last row: [5. 6.]
First item in last column: 2.0
Skip the first row:
[[3. 4.]
 [5. 6.]] 


นี่คือตัวอย่างของเทนเซอร์ 3 แกน:

print(rank_3_tensor[:, :, 4])
tf.Tensor(
[[ 4  9]
 [14 19]
 [24 29]], shape=(3, 2), dtype=int32)

การเลือกคุณลักษณะสุดท้ายในตำแหน่งทั้งหมดในแต่ละตัวอย่างในชุดงาน
เทนเซอร์ 3x2x5 ที่มีค่าทั้งหมดที่ดัชนี -4 ของแกนสุดท้ายที่เลือกค่าที่เลือกบรรจุในเทนเซอร์ 2 แกน

อ่าน คู่มือการแบ่ง ส่วน เทนเซอร์ เพื่อเรียนรู้ว่าคุณสามารถใช้การจัดทำดัชนีเพื่อจัดการกับองค์ประกอบแต่ละอย่างในเทนเซอร์ของคุณ

การจัดการรูปร่าง

การปรับรูปร่างเทนเซอร์เป็นประโยชน์อย่างมาก

# Shape returns a `TensorShape` object that shows the size along each axis
x = tf.constant([[1], [2], [3]])
print(x.shape)
(3, 1)

# You can convert this object into a Python list, too
print(x.shape.as_list())
[3, 1]

คุณสามารถปรับรูปร่างเทนเซอร์ให้เป็นรูปร่างใหม่ได้ การดำเนินการ tf.reshape นั้นรวดเร็วและราคาถูกเนื่องจากข้อมูลพื้นฐานไม่จำเป็นต้องทำซ้ำ

# You can reshape a tensor to a new shape.
# Note that you're passing in a list
reshaped = tf.reshape(x, [1, 3])
print(x.shape)
print(reshaped.shape)
(3, 1)
(1, 3)

ข้อมูลจะรักษาเค้าโครงไว้ในหน่วยความจำและมีการสร้างเทนเซอร์ใหม่โดยมีรูปร่างที่ร้องขอโดยชี้ไปที่ข้อมูลเดียวกัน TensorFlow ใช้การจัดลำดับหน่วยความจำแบบ "row-major" แบบ C ซึ่งการเพิ่มดัชนีขวาสุดจะสอดคล้องกับขั้นตอนเดียวในหน่วยความจำ

print(rank_3_tensor)
tf.Tensor(
[[[ 0  1  2  3  4]
  [ 5  6  7  8  9]]

 [[10 11 12 13 14]
  [15 16 17 18 19]]

 [[20 21 22 23 24]
  [25 26 27 28 29]]], shape=(3, 2, 5), dtype=int32)

ถ้าคุณแบนเทนเซอร์คุณจะเห็นว่ามันเรียงลำดับอะไรในหน่วยความจำ

# A `-1` passed in the `shape` argument says "Whatever fits".
print(tf.reshape(rank_3_tensor, [-1]))
tf.Tensor(
[ 0  1  2  3  4  5  6  7  8  9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
 24 25 26 27 28 29], shape=(30,), dtype=int32)

โดยปกติการใช้ tf.reshape อย่างสมเหตุสมผลเพียงอย่างเดียวคือการรวมหรือแยกแกนที่อยู่ติดกัน (หรือเพิ่ม / ลบ 1 วินาที)

สำหรับเทนเซอร์ 3x2x5 นี้การปรับรูปร่างใหม่เป็น (3x2) x5 หรือ 3x (2x5) เป็นสิ่งที่สมเหตุสมผลที่ต้องทำเนื่องจากชิ้นส่วนไม่ผสมกัน:

print(tf.reshape(rank_3_tensor, [3*2, 5]), "\n")
print(tf.reshape(rank_3_tensor, [3, -1]))
tf.Tensor(
[[ 0  1  2  3  4]
 [ 5  6  7  8  9]
 [10 11 12 13 14]
 [15 16 17 18 19]
 [20 21 22 23 24]
 [25 26 27 28 29]], shape=(6, 5), dtype=int32) 

tf.Tensor(
[[ 0  1  2  3  4  5  6  7  8  9]
 [10 11 12 13 14 15 16 17 18 19]
 [20 21 22 23 24 25 26 27 28 29]], shape=(3, 10), dtype=int32)

รูปร่างที่ดีบางอย่าง
เทนเซอร์ 3x2x5ข้อมูลเดียวกันเปลี่ยนรูปเป็น (3x2) x5ข้อมูลเดียวกันเปลี่ยนรูปเป็น 3x (2x5)

การปรับรูปร่างใหม่จะ "ใช้ได้ผล" สำหรับรูปร่างใหม่ใด ๆ ที่มีจำนวนองค์ประกอบทั้งหมดเท่ากัน แต่จะไม่เกิดประโยชน์อะไรหากคุณไม่เคารพลำดับของแกน

การสลับแกนใน tf.reshape ไม่ทำงาน คุณต้องการ tf.transpose สำหรับสิ่งนั้น

# Bad examples: don't do this

# You can't reorder axes with reshape.
print(tf.reshape(rank_3_tensor, [2, 3, 5]), "\n") 

# This is a mess
print(tf.reshape(rank_3_tensor, [5, 6]), "\n")

# This doesn't work at all
try:
  tf.reshape(rank_3_tensor, [7, -1])
except Exception as e:
  print(f"{type(e).__name__}: {e}")
tf.Tensor(
[[[ 0  1  2  3  4]
  [ 5  6  7  8  9]
  [10 11 12 13 14]]

 [[15 16 17 18 19]
  [20 21 22 23 24]
  [25 26 27 28 29]]], shape=(2, 3, 5), dtype=int32) 

tf.Tensor(
[[ 0  1  2  3  4  5]
 [ 6  7  8  9 10 11]
 [12 13 14 15 16 17]
 [18 19 20 21 22 23]
 [24 25 26 27 28 29]], shape=(5, 6), dtype=int32) 

InvalidArgumentError: Input to reshape is a tensor with 30 values, but the requested shape requires a multiple of 7 [Op:Reshape]

รูปร่างที่ไม่ดีบางอย่าง
คุณไม่สามารถเรียงลำดับแกนใหม่ได้ให้ใช้ tf.transpose สำหรับสิ่งนั้นอะไรก็ตามที่ผสมส่วนของข้อมูลเข้าด้วยกันอาจเป็นสิ่งที่ผิดทรงใหม่ต้องพอดีเป๊ะ

คุณสามารถวิ่งข้ามรูปร่างที่ไม่ได้ระบุไว้อย่างครบถ้วน ทั้งรูปร่างจะประกอบด้วย None (ไม่ทราบความยาวแกน) หรือรูปร่างทั้งหมดเป็น None ( None ทราบอันดับของเทนเซอร์)

ยกเว้น tf.RaggedTensor รูปร่างดังกล่าวจะเกิดขึ้นในบริบทของ API ที่สร้างกราฟเชิงสัญลักษณ์ของ TensorFlow เท่านั้น:

เพิ่มเติมเกี่ยวกับ DTypes

ในการตรวจสอบ tf.Tensor ชนิดข้อมูลการใช้งานของTensor.dtype คุณสมบัติ

เมื่อสร้าง tf.Tensor จากออบเจ็กต์ Python คุณสามารถเลือกระบุประเภทข้อมูลได้

ถ้าคุณไม่ทำเช่นนั้น TensorFlow จะเลือกประเภทข้อมูลที่สามารถแสดงข้อมูลของคุณได้ TensorFlow แปลงจำนวนเต็ม Python เป็น tf.int32 และ Python floating point เป็น tf.float32 มิฉะนั้น TensorFlow จะใช้กฎเดียวกันกับที่ NumPy ใช้เมื่อแปลงเป็นอาร์เรย์

คุณสามารถส่งจากประเภทหนึ่งไปยังอีกประเภทหนึ่งได้

the_f64_tensor = tf.constant([2.2, 3.3, 4.4], dtype=tf.float64)
the_f16_tensor = tf.cast(the_f64_tensor, dtype=tf.float16)
# Now, cast to an uint8 and lose the decimal precision
the_u8_tensor = tf.cast(the_f16_tensor, dtype=tf.uint8)
print(the_u8_tensor)
tf.Tensor([2 3 4], shape=(3,), dtype=uint8)

การแพร่ภาพ

การแพร่ภาพเป็นแนวคิดที่ยืมมาจาก คุณลักษณะที่เทียบเท่าใน NumPy ในระยะสั้นภายใต้เงื่อนไขบางประการเทนเซอร์ที่มีขนาดเล็กจะถูก "ยืดออก" โดยอัตโนมัติเพื่อให้พอดีกับเทนเซอร์ที่มีขนาดใหญ่ขึ้นเมื่อเรียกใช้การทำงานร่วมกัน

กรณีที่ง่ายและพบบ่อยที่สุดคือเมื่อคุณพยายามคูณหรือเพิ่มเทนเซอร์ให้กับสเกลาร์ ในกรณีนั้นสเกลาร์จะถูกถ่ายทอดเป็นรูปร่างเดียวกับอาร์กิวเมนต์อื่น

x = tf.constant([1, 2, 3])

y = tf.constant(2)
z = tf.constant([2, 2, 2])
# All of these are the same computation
print(tf.multiply(x, 2))
print(x * y)
print(x * z)
tf.Tensor([2 4 6], shape=(3,), dtype=int32)
tf.Tensor([2 4 6], shape=(3,), dtype=int32)
tf.Tensor([2 4 6], shape=(3,), dtype=int32)

ในทำนองเดียวกันแกนที่มีความยาว 1 สามารถยืดออกเพื่อให้ตรงกับอาร์กิวเมนต์อื่น ๆ อาร์กิวเมนต์ทั้งสองสามารถยืดออกได้ในการคำนวณเดียวกัน

ในกรณีนี้เมทริกซ์ 3x1 คือองค์ประกอบที่ชาญฉลาดคูณด้วยเมทริกซ์ 1x4 เพื่อสร้างเมทริกซ์ 3x4 สังเกตว่า 1 นำหน้าเป็นทางเลือกอย่างไร: รูปร่างของ y คือ [4]

# These are the same computations
x = tf.reshape(x,[3,1])
y = tf.range(1, 5)
print(x, "\n")
print(y, "\n")
print(tf.multiply(x, y))
tf.Tensor(
[[1]
 [2]
 [3]], shape=(3, 1), dtype=int32) 

tf.Tensor([1 2 3 4], shape=(4,), dtype=int32) 

tf.Tensor(
[[ 1  2  3  4]
 [ 2  4  6  8]
 [ 3  6  9 12]], shape=(3, 4), dtype=int32)

การเพิ่มที่ออกอากาศ: a [3, 1] คูณ a [1, 4] ให้ [3,4]
การเพิ่มเมทริกซ์ 3x1 ลงในเมทริกซ์ 4x1 ผลลัพธ์ในเมทริกซ์ 3x4

นี่คือการดำเนินการเดียวกันโดยไม่ต้องออกอากาศ:

x_stretch = tf.constant([[1, 1, 1, 1],
                         [2, 2, 2, 2],
                         [3, 3, 3, 3]])

y_stretch = tf.constant([[1, 2, 3, 4],
                         [1, 2, 3, 4],
                         [1, 2, 3, 4]])

print(x_stretch * y_stretch)  # Again, operator overloading
tf.Tensor(
[[ 1  2  3  4]
 [ 2  4  6  8]
 [ 3  6  9 12]], shape=(3, 4), dtype=int32)

เวลาส่วนใหญ่การออกอากาศมีทั้งเวลาและพื้นที่อย่างมีประสิทธิภาพเนื่องจากการดำเนินการออกอากาศไม่เคยทำให้เกิดเทนเซอร์ที่ขยายในหน่วยความจำ

คุณจะเห็นว่าการออกอากาศเป็นอย่างไรเมื่อใช้tf.broadcast_to

print(tf.broadcast_to(tf.constant([1, 2, 3]), [3, 3]))
tf.Tensor(
[[1 2 3]
 [1 2 3]
 [1 2 3]], shape=(3, 3), dtype=int32)

ซึ่งแตกต่างจาก op ทางคณิตศาสตร์ตัวอย่างเช่น broadcast_to ไม่ได้ทำอะไรเป็นพิเศษในการบันทึกหน่วยความจำ ที่นี่คุณกำลังเป็นตัวเป็นตนของเทนเซอร์

มันจะซับซ้อนมากขึ้น ส่วนนี้ ของหนังสือ Python Data Science Handbook ของ Jake VanderPlas แสดงเทคนิคการออกอากาศเพิ่มเติม (อีกครั้งใน NumPy)

tf.convert_to_tensor

ops ส่วนใหญ่เช่น tf.matmul และ tf.reshape ใช้อาร์กิวเมนต์ของ class tf.Tensor อย่างไรก็ตามคุณจะสังเกตเห็นในกรณีข้างต้นว่ายอมรับวัตถุ Python ที่มีรูปร่างเหมือนเทนเซอร์

ตัวเลือกส่วนใหญ่ แต่ไม่ใช่ทั้งหมดเรียก convert_to_tensor บนอาร์กิวเมนต์ที่ไม่ใช่เทนเซอร์ มีรีจิสทรีของการแปลงและคลาสอ็อบเจ็กต์ส่วนใหญ่เช่น ndarray ของ NumPy, TensorShape , รายการ Python และ tf.Variable ทั้งหมดจะแปลงโดยอัตโนมัติ

ดู tf.register_tensor_conversion_function สำหรับรายละเอียดเพิ่มเติมและหากคุณมีประเภทของตัวเองคุณต้องการแปลงเป็นเทนเซอร์โดยอัตโนมัติ

Ragged Tensors

เทนเซอร์ที่มีจำนวนองค์ประกอบแปรผันตามแกนบางส่วนเรียกว่า "มอมแมม" ใช้ tf.ragged.RaggedTensor สำหรับข้อมูลที่ไม่สมบูรณ์

ตัวอย่างเช่นสิ่งนี้ไม่สามารถแสดงเป็นเทนเซอร์ปกติได้:

tf.RaggedTensor รูปร่าง: [4, None]
เทนเซอร์แบบมอมแมม 2 แกนแต่ละแถวมีความยาวต่างกัน
ragged_list = [
    [0, 1, 2, 3],
    [4, 5],
    [6, 7, 8],
    [9]]
try:
  tensor = tf.constant(ragged_list)
except Exception as e:
  print(f"{type(e).__name__}: {e}")
ValueError: Can't convert non-rectangular Python sequence to Tensor.

สร้างtf.RaggedTensor โดยใช้ tf.ragged.constant :

ragged_tensor = tf.ragged.constant(ragged_list)
print(ragged_tensor)
<tf.RaggedTensor [[0, 1, 2, 3], [4, 5], [6, 7, 8], [9]]>

รูปร่างของtf.RaggedTensor จะมีแกนบางส่วนที่ไม่ทราบความยาว:

print(ragged_tensor.shape)
(4, None)

สตริงเทนเซอร์

tf.string คือ dtype ซึ่งหมายความว่าคุณสามารถแทนข้อมูลเป็นสตริง (อาร์เรย์ไบต์ที่มีความยาวตัวแปร) ในเทนเซอร์

สตริงเป็นแบบอะตอมและไม่สามารถจัดทำดัชนีได้ตามที่สตริง Python เป็น ความยาวของสตริงไม่ใช่หนึ่งในแกนของเทนเซอร์ โปรดดูที่ tf.strings สำหรับฟังก์ชันในการจัดการ

นี่คือเทนเซอร์สตริงสเกลาร์:

# Tensors can be strings, too here is a scalar string.
scalar_string_tensor = tf.constant("Gray wolf")
print(scalar_string_tensor)
tf.Tensor(b'Gray wolf', shape=(), dtype=string)

และเวกเตอร์ของสตริง:

เวกเตอร์ของสตริงรูปร่าง: [3,]
ความยาวสตริงไม่ใช่หนึ่งในแกนของเทนเซอร์
# If you have three string tensors of different lengths, this is OK.
tensor_of_strings = tf.constant(["Gray wolf",
                                 "Quick brown fox",
                                 "Lazy dog"])
# Note that the shape is (3,). The string length is not included.
print(tensor_of_strings)
tf.Tensor([b'Gray wolf' b'Quick brown fox' b'Lazy dog'], shape=(3,), dtype=string)

ในการพิมพ์ด้านบนคำนำหน้า b ระบุว่า tf.string dtype ไม่ใช่สตริงยูนิโคด แต่เป็นไบต์สตริง ดู บทช่วยสอน Unicode สำหรับข้อมูลเพิ่มเติมเกี่ยวกับการทำงานกับข้อความ Unicode ใน TensorFlow

หากคุณส่งอักขระ Unicode พวกเขาจะเข้ารหัส utf-8

tf.constant("🥳👍")
<tf.Tensor: shape=(), dtype=string, numpy=b'\xf0\x9f\xa5\xb3\xf0\x9f\x91\x8d'>

ฟังก์ชันพื้นฐานบางอย่างที่มีสตริงสามารถพบได้ใน tf.strings รวมถึง tf.strings.split

# You can use split to split a string into a set of tensors
print(tf.strings.split(scalar_string_tensor, sep=" "))
tf.Tensor([b'Gray' b'wolf'], shape=(2,), dtype=string)

# ...but it turns into a `RaggedTensor` if you split up a tensor of strings,
# as each string might be split into a different number of parts.
print(tf.strings.split(tensor_of_strings))
<tf.RaggedTensor [[b'Gray', b'wolf'], [b'Quick', b'brown', b'fox'], [b'Lazy', b'dog']]>

สามสายแบ่งรูปร่าง: [3, None]
การแยกสตริงหลายสตริงจะส่งคืน tf.RaggedTensor

และ tf.string.to_number :

text = tf.constant("1 10 100")
print(tf.strings.to_number(tf.strings.split(text, " ")))
tf.Tensor([  1.  10. 100.], shape=(3,), dtype=float32)

แม้ว่าคุณจะไม่สามารถใช้ tf.cast เพื่อเปลี่ยนเทนเซอร์สตริงให้เป็นตัวเลขได้ แต่คุณสามารถแปลงเป็นไบต์แล้วเป็นตัวเลขได้

byte_strings = tf.strings.bytes_split(tf.constant("Duck"))
byte_ints = tf.io.decode_raw(tf.constant("Duck"), tf.uint8)
print("Byte strings:", byte_strings)
print("Bytes:", byte_ints)
Byte strings: tf.Tensor([b'D' b'u' b'c' b'k'], shape=(4,), dtype=string)
Bytes: tf.Tensor([ 68 117  99 107], shape=(4,), dtype=uint8)

# Or split it up as unicode and then decode it
unicode_bytes = tf.constant("アヒル 🦆")
unicode_char_bytes = tf.strings.unicode_split(unicode_bytes, "UTF-8")
unicode_values = tf.strings.unicode_decode(unicode_bytes, "UTF-8")

print("\nUnicode bytes:", unicode_bytes)
print("\nUnicode chars:", unicode_char_bytes)
print("\nUnicode values:", unicode_values)

Unicode bytes: tf.Tensor(b'\xe3\x82\xa2\xe3\x83\x92\xe3\x83\xab \xf0\x9f\xa6\x86', shape=(), dtype=string)

Unicode chars: tf.Tensor([b'\xe3\x82\xa2' b'\xe3\x83\x92' b'\xe3\x83\xab' b' ' b'\xf0\x9f\xa6\x86'], shape=(5,), dtype=string)

Unicode values: tf.Tensor([ 12450  12498  12523     32 129414], shape=(5,), dtype=int32)

tf.string dtype ใช้สำหรับข้อมูลไบต์ดิบทั้งหมดใน TensorFlow โมดูล tf.io มีฟังก์ชันสำหรับการแปลงข้อมูลไปและกลับจากไบต์รวมถึงการถอดรหัสรูปภาพและการแยกวิเคราะห์ csv

เทนเซอร์เบาบาง

บางครั้งข้อมูลของคุณก็กระจัดกระจายเช่นพื้นที่ฝังที่กว้างมาก TensorFlow รองรับ tf.sparse.SparseTensor และการดำเนินการที่เกี่ยวข้องเพื่อจัดเก็บข้อมูลที่กระจัดกระจายอย่างมีประสิทธิภาพ

tf.SparseTensor รูปร่าง: [3, 4]
ตาราง 3x4 ที่มีค่าเพียงสองเซลล์
# Sparse tensors store values by index in a memory-efficient manner
sparse_tensor = tf.sparse.SparseTensor(indices=[[0, 0], [1, 2]],
                                       values=[1, 2],
                                       dense_shape=[3, 4])
print(sparse_tensor, "\n")

# You can convert sparse tensors to dense
print(tf.sparse.to_dense(sparse_tensor))
SparseTensor(indices=tf.Tensor(
[[0 0]
 [1 2]], shape=(2, 2), dtype=int64), values=tf.Tensor([1 2], shape=(2,), dtype=int32), dense_shape=tf.Tensor([3 4], shape=(2,), dtype=int64)) 

tf.Tensor(
[[1 0 0 0]
 [0 0 2 0]
 [0 0 0 0]], shape=(3, 4), dtype=int32)