加法的广播机制
import torch
# 创建原始张量
a = torch.tensor([[10], [20], [30]]) # 形状: (3, 1)
b = torch.tensor([1, 2, 3]) # 形状: (3,)
result = a + b
# 广播过程
# 1. b补全维度: (3,) → (1, 3)
# 2. a扩展列: (3, 1) → (3, 3)
# 3. b扩展行: (1, 3) → (3, 3)
# 最终形状: (3, 3)
print("原始张量a:")
print(a)
print("\n原始张量b:")
print(b)
print("\n广播后a的值扩展:")
print(torch.tensor([[10, 10, 10],
[20, 20, 20],
[30, 30, 30]])) # 实际内存中未复制,仅逻辑上扩展
print("\n广播后b的值扩展:")
print(torch.tensor([[1, 2, 3],
[1, 2, 3],
[1, 2, 3]])) # 实际内存中未复制,仅逻辑上扩展
print("\n加法结果:")
print(result)
三维张量与二维张量相加
# 创建原始张量
a = torch.tensor([[[1], [2]], [[3], [4]]]) # 形状: (2, 2, 1)
b = torch.tensor([[10, 20]]) # 形状: (1, 2)
# 广播过程
# 1. b补全维度: (1, 2) → (1, 1, 2)
# 2. a扩展第三维: (2, 2, 1) → (2, 2, 2)
# 3. b扩展第一维: (1, 1, 2) → (2, 1, 2)
# 4. b扩展第二维: (2, 1, 2) → (2, 2, 2)
# 最终形状: (2, 2, 2)
result = a + b
print("原始张量a:")
print(a)
print("\n原始张量b:")
print(b)
print("\n广播后a的值扩展:")
print(torch.tensor([[[1, 1],
[2, 2]],
[[3, 3],
[4, 4]]])) # 实际内存中未复制,仅逻辑上扩展
print("\n广播后b的值扩展:")
print(torch.tensor([[[10, 20],
[10, 20]],
[[10, 20],
[10, 20]]])) # 实际内存中未复制,仅逻辑上扩展
print("\n加法结果:")
print(result)
二维张量与标亮相加
# 创建原始张量
a = torch.tensor([[1, 2], [3, 4]]) # 形状: (2, 2)
b = 10 # 标量,形状视为 ()
# 广播过程
# 1. b补全维度: () → (1, 1)
# 2. b扩展第一维: (1, 1) → (2, 1)
# 3. b扩展第二维: (2, 1) → (2, 2)
# 最终形状: (2, 2)
result = a + b
print("原始张量a:")
print(a)
# 输出:
# tensor([[1, 2],
# [3, 4]])
print("\n标量b:")
print(b)
# 输出: 10
print("\n广播后b的值扩展:")
print(torch.tensor([[10, 10],
[10, 10]])) # 实际内存中未复制,仅逻辑上扩展
print("\n加法结果:")
print(result)
# 输出:
# tensor([[11, 12],
# [13, 14]])
高维张量与地维张量相加
# 创建原始张量
a = torch.tensor([[[1, 2], [3, 4]]]) # 形状: (1, 2, 2)
b = torch.tensor([[5, 6]]) # 形状: (1, 2)
# 广播过程
# 1. b补全维度: (1, 2) → (1, 1, 2)
# 2. b扩展第二维: (1, 1, 2) → (1, 2, 2)
# 最终形状: (1, 2, 2)
result = a + b
print("原始张量a:")
print(a)
# 输出:
# tensor([[[1, 2],
# [3, 4]]])
print("\n原始张量b:")
print(b)
# 输出:
# tensor([[5, 6]])
print("\n广播后b的值扩展:")
print(torch.tensor([[[5, 6],
[5, 6]]])) # 实际内存中未复制,仅逻辑上扩展
print("\n加法结果:")
print(result)
# 输出:
# tensor([[[6, 8],
# [8, 10]]])
乘法的广播机制
批量矩阵与单个矩阵相乘
import torch
# A: 批量大小为2,每个是3×4的矩阵
A = torch.randn(2, 3, 4) # 形状: (2, 3, 4)
# B: 单个4×5的矩阵
B = torch.randn(4, 5) # 形状: (4, 5)
# 广播过程:
# 1. B补全维度: (4, 5) → (1, 4, 5)
# 2. B扩展第一维: (1, 4, 5) → (2, 4, 5)
# 矩阵乘法: (2, 3, 4) @ (2, 4, 5) → (2, 3, 5)
result = A @ B # 结果形状: (2, 3, 5)
print("A形状:", A.shape) # 输出: torch.Size([2, 3, 4])
print("B形状:", B.shape) # 输出: torch.Size([4, 5])
print("结果形状:", result.shape) # 输出: torch.Size([2, 3, 5])
批量矩阵与批量矩阵相乘
# A: 批量大小为3,每个是2×4的矩阵
A = torch.randn(3, 2, 4) # 形状: (3, 2, 4)
# B: 批量大小为1,每个是4×5的矩阵
B = torch.randn(1, 4, 5) # 形状: (1, 4, 5)
# 广播过程:
# B扩展第一维: (1, 4, 5) → (3, 4, 5)
# 矩阵乘法: (3, 2, 4) @ (3, 4, 5) → (3, 2, 5)
result = A @ B # 结果形状: (3, 2, 5)
print("A形状:", A.shape) # 输出: torch.Size([3, 2, 4])
print("B形状:", B.shape) # 输出: torch.Size([1, 4, 5])
print("结果形状:", result.shape) # 输出: torch.Size([3, 2, 5])
三维张量与二维张量相乘
# A: 批量大小为2,通道数为3,每个是4×5的矩阵
A = torch.randn(2, 3, 4, 5) # 形状: (2, 3, 4, 5)
# B: 单个5×6的矩阵
B = torch.randn(5, 6) # 形状: (5, 6)
# 广播过程:
# 1. B补全维度: (5, 6) → (1, 1, 5, 6)
# 2. B扩展第一维: (1, 1, 5, 6) → (2, 1, 5, 6)
# 3. B扩展第二维: (2, 1, 5, 6) → (2, 3, 5, 6)
# 矩阵乘法: (2, 3, 4, 5) @ (2, 3, 5, 6) → (2, 3, 4, 6)
result = A @ B # 结果形状: (2, 3, 4, 6)
print("A形状:", A.shape) # 输出: torch.Size([2, 3, 4, 5])
print("B形状:", B.shape) # 输出: torch.Size([5, 6])
print("结果形状:", result.shape) # 输出: torch.Size([2, 3, 4, 6])

被折叠的 条评论
为什么被折叠?



