嵌入式学习-PyTorch(3)-day20

transforms结构及用法

transforms.yp是一个工具箱

就是将一个特定格式的图片经过这个工具的到想要的变换

Tensor数据类型


一、transforms 的使用(Python)

from PIL import Image
from torch.utils.tensorboard import SummaryWriter
from torchvision import transforms

writer = SummaryWriter("logs")
img = Image.open("images/微信图片_20250711193055.jpg")
print(img)
#ToTensor
trans_totensor = transforms.ToTensor()
img_tensor = trans_totensor(img)
writer.add_image("ToTensor", img_tensor)

#Normalize
trans_norm = transforms.Normalize([0.5, 0.5, 0.5], [0.5, 0.5, 0.5])
img_norm = trans_norm(img_tensor)
writer.add_image("Normalize", img_norm)

#Resize
print(img.size)
trans_resize = transforms.Resize((512, 512))
img_resize = trans_resize(img)
print(img_resize)
img_resize = trans_totensor(img_resize)

writer.add_image("Resize", img_resize,1)

#Compose - resize - 2
trans_resize_2 = transforms.Resize((512, 512))
trans_compose = transforms.Compose([trans_resize_2, trans_totensor])
img_resize_2 = trans_compose(img)
writer.add_image("Compose", img_resize_2,2)

#RandomCrop
trans_random = transforms.RandomCrop(512,1024)
trans_compose_2 = transforms.Compose([trans_random,trans_totensor])
for i in range(10):
    img_crop = trans_compose_2(img)
    writer.add_image("RandomCropHW", img_crop,i)

writer.close()

transformstorchvision 的一个模块,专门用来做 图片的预处理和数据增强

核心用法:

from torchvision import transforms

transform = transforms.ToTensor()

image = Image.open('xxx.jpg') # PIL Image

tensor_image = transform(image) # 转成 Tensor

常用的组合写法

transform = transforms.Compose([

transforms.Resize((224, 224)),

transforms.ToTensor(),

])

image = Image.open('xxx.jpg')

tensor_image = transform(image)

transforms.Compose() 可以把多个预处理步骤按顺序连接起来,比如缩放、裁剪、转 Tensor 等。


ToTensor 的具体作用:

  • 输入:PIL Image(或 numpy ndarray)

  • 输出:FloatTensor,shape 为 [C, H, W],像素值范围变成 [0.0, 1.0]

  • 转换细节:

    • RGB 图片:shape (H, W, 3) ➡️ (3, H, W)

    • 像素值:0-255 的 uint8 ➡️ 浮点数 0-1 之间

例子:

from PIL import Image

from torchvision import transforms

img = Image.open('xxx.jpg')

tensor = transforms.ToTensor()(img)

print(tensor.shape) # torch.Size([3, H, W])

print(tensor.max(), tensor.min()) # tensor.max() 应该接近 1.0,min() 接近 0.0


二、为什么我们需要 Tensor 数据类型

Tensor 就是 PyTorch 的核心数据结构,类似于 NumPy 的 ndarray,但它具备 GPU 加速、自动求导 的能力。

功能 普通数组(如 numpy) Tensor
CPU 运算 ✅ 支持 ✅ 支持
GPU 运算 ❌ 不支持 ✅ 支持
自动求导(梯度计算) ❌ 不支持 ✅ 支持
深度学习框架兼容性 ❌ 基础数学计算 ✅ 完全兼容 PyTorch

主要原因:

  • 高效: PyTorch 的训练推理只能用 Tensor,尤其是 GPU 运算

  • 梯度计算: Tensor 支持 requires_grad=True,训练模型时自动求导

  • 统一数据接口: 图片转成 Tensor 后,数据可以无缝送入 DataLoader、模型训练

简单例子:

import torch a = torch.tensor([[1.0, 2.0], [3.0, 4.0]], requires_grad=True)

b = a * 2

c = b.mean()

c.backward()

print(a.grad) # 自动求导,得到梯度


✅ 总结:

问题 精炼回答
transforms怎么用 Compose 串联多个预处理方法,用 ToTensor 把图片转成 FloatTensor,范围 0-1,格式 [C, H, W]
为什么要 Tensor Tensor 支持 GPU 运算、自动求导、直接送入模型训练,是 PyTorch 的“标配数据类型”

 

一、Compose函数

transforms.Compose 是什么?

Compose 的作用:将一系列图片预处理操作“打包”成一个整体,一次性执行多个转换。

使用场景:数据预处理步骤往往不止一条,比如:

  • resize 调整图片大小

  • center crop 居中裁剪

  • ToTensor 转 Tensor

  • Normalize 标准化

Compose 可以这样串起来:

from torchvision import transforms

transform = transforms.Compose([

transforms.Resize((224, 224)),

transforms.ToTensor(),

transforms.Normalize(mean=[0.5], std=[0.5])

])

执行逻辑Compose按顺序 对图片执行这些操作。

比如:

from PIL import Image

img = Image.open("xxx.jpg")

img = transform(img) # 按顺序执行 Resize ➡️ ToTensor ➡️ Normalize

简单理解:Compose 就是一个“流程线”,把多个变换打包成一个函数

二、Normalize函数

transforms.Normalize 是什么?

作用:

将图片的每个通道(通常是 RGB 三个通道)按均值和标准差进行归一化,让数据符合标准正态分布(均值0,标准差1),便于模型更快收敛、训练更稳定。

数学公式:

\text{output} = \frac{\text{input} - \text{mean}}{\text{std}}


常见用法:

transforms.Normalize(mean=[0.485, 0.456, 0.406], 
                     std=[0.229, 0.224, 0.225])
  • meanstd 分别对应 每个通道的均值和标准差

  • 例如 RGB 三通道,就填 [mean_R, mean_G, mean_B][std_R, std_G, std_B]


例子拆解:

假设输入图片的像素值已经通过 ToTensor() 转为 [0,1] 的 Tensor,Normalize() 会:

  • 每个像素先减去 mean

  • 再除以 std

  • 最终得到既可以有负数也可以大于1的 标准化 Tensor

常见 ImageNet 预训练模型标准化参数

transforms.Normalize(mean=[0.485, 0.456, 0.406], std=[0.229, 0.224, 0.225])

这些 mean/std 来自于 ImageNet 数据集整体统计值。


为什么 Normalize 很重要:

目的 解释
加速模型收敛 数据归一化后能避免某些特征“值特别大”,训练更平滑
特征居中 均值变成0,避免偏移现象
兼容预训练模型 训练和推理保持一致(不归一化直接喂模型会效果很差!)


⚡完整案例:从图片到标准化 Tensor

from torchvision import transforms
from PIL import Image

transform = transforms.Compose([
    transforms.Resize((224,224)),
    transforms.ToTensor(),
    transforms.Normalize(mean=[0.485,0.456,0.406], std=[0.229,0.224,0.225])
])

img = Image.open('cat.jpg')
tensor = transform(img)
print(tensor.shape)  # torch.Size([3, 224, 224])
print(f"最大值:{tensor.max()}, 最小值:{tensor.min()}")

小总结:

模块 功能 举例说明
ToTensor() 转为 Tensor,归一化到 [0,1] RGB 图片 ➡️ Tensor
Normalize() 标准化到均值0方差1 减均值除方差

 

 三、Resize函数

transforms.Resize 是什么?

作用:

Resize 用于 调整图片大小,不论你的原图是啥尺寸,它都可以帮你按指定方式变成固定尺寸,方便送入神经网络训练或推理。

为什么需要 Resize:

  • 统一输入大小:神经网络通常要求输入固定尺寸(比如 ResNet 要 224×224)

  • 降低运算量:原图太大训练成本高

  • 数据增强的一部分:Resize 搭配其他 transform 使用效果更佳


✨ 基础用法

1. 指定固定尺寸

from torchvision import transforms 
transform = transforms.Resize((224, 224))

效果:

  • 无论输入什么尺寸,强制缩放到 224x224保持 [H, W]


2. 指定单个整数

transform = transforms.Resize(224)

效果:

  • 按短边缩放为 224长边按比例缩放,保持长宽比不变

例子:

  • 输入图片 300×500 ➡️ 输出 224×374

  • 输入图片 1000×800 ➡️ 输出 224×179


支持参数

Resize(size, interpolation=InterpolationMode.BILINEAR, max_size=None, antialias=None)
  • size: (H, W) 或 单个 int

  • interpolation: 插值算法(默认 BILINEAR)

  • max_size: 当 size 是单个整数时,可以控制最大边长

  • antialias: 是否使用抗锯齿(PyTorch 2.0 起推荐)


插值模式

模式 说明
InterpolationMode.BILINEAR 双线性插值(默认,平滑效果好)
InterpolationMode.NEAREST 最近邻(速度快但不平滑)
InterpolationMode.BICUBIC 三次样条插值(更平滑但慢)

例子:

from torchvision.transforms import InterpolationMode 
transform = transforms.Resize((128, 128), interpolation=InterpolationMode.BICUBIC)

完整示例

from torchvision import transforms
from PIL import Image

img = Image.open('dog.jpg')
transform = transforms.Compose([
    transforms.Resize((128, 128)),
    transforms.ToTensor()
])

tensor_img = transform(img)
print(tensor_img.shape)  # torch.Size([3, 128, 128])

⚡ 小总结

功能 说明
Resize((H, W)) 直接缩放到 H×W, 强行拉伸
Resize(H) 短边变成 H, 长边等比例缩放
interpolation 控制缩放质量
常配合 通常和 ToTensor()Normalize() 一起使用

四、RandomCrop

transforms.RandomCrop 是什么?

核心功能:

  • 随机裁剪图片的一块区域

  • 在训练时引入随机性,提升模型对图片位置、特征分布的鲁棒性(抗干扰能力)

  • Resize 不同,RandomCrop 不是缩放,而是“剪一块下来”


✨ 常见用法

1. 最简单的裁剪:
from torchvision import transforms

transform = transforms.RandomCrop(size=(224, 224))

效果:

  • 输入图片会随机裁剪出一个 224×224 的小区域,丢弃剩下的部分。

  • 如果图片尺寸小于裁剪区域,会报错。


2. 裁剪后自动 resize:

通常搭配 Resize 用于先缩放再裁剪:

transform = transforms.Compose([
    transforms.Resize(256),         # 确保图片至少256的短边
    transforms.RandomCrop(224),     # 裁剪224×224的区域
    transforms.ToTensor()
])

典型 ImageNet 标配套路:先Resize到256 ➡️ 再随机裁剪224


3. 可选参数(高级玩法):
RandomCrop(size, padding=0, pad_if_needed=False, fill=0, padding_mode='constant')
参数 含义
size 裁剪的输出尺寸
padding 随机裁剪前先加上四周 padding
pad_if_needed 如果原图小于 size,是否自动 pad
fill 填充值(仅 padding_mode=constant 时生效)
padding_mode constant(默认零填充)、edge(边界值填充)、reflect(镜像填充)

例子:
transform = transforms.RandomCrop(224, padding=16, padding_mode='reflect')

效果:

  • 图片四周先镜像扩展 16 像素,再随机裁剪 224×224


为什么用 RandomCrop?

场景 理由
防止过拟合 模型不能只记住图片的某个固定区域
增加数据多样性 每次训练模型看到的“图片”都不同
空间不变性 让模型学到特征不局限于图片中心


完整示例

from torchvision import transforms
from PIL import Image

transform = transforms.Compose([
    transforms.Resize(256),
    transforms.RandomCrop(224),
    transforms.ToTensor()
])

img = Image.open('cat.jpg')
tensor = transform(img)
print(tensor.shape)  # torch.Size([3, 224, 224])


✅ 小总结

模块 功能 作用
Resize 缩放图片 固定尺寸输入
RandomCrop 随机裁剪 增加随机性,提升泛化能力
ToTensor 转 Tensor PyTorch 标配

你可能感兴趣的:(学习,pytorch,人工智能)