为什么在图像处理中要使用Unsqueeze()函数?

3

我正在尝试完成一项指导项目,与图像处理有关。在进行图像处理时,导师使用了Unsqueeze(0)函数来设置床的大小。我想知道更改床的大小后会发生什么。以下是您参考的代码。

如果您能快速回复,我将非常感激。

from torchvision import transforms as T

def preprocess(img_path,max_size = 500):
  image = Image.open(img_path).convert('RGB')

  if max(image.size) > max_size:
    size = max_size
  else:
    size = max(image.size)

  img_transform = T.Compose([
                             T.Resize(size),
                             T.ToTensor(),
                             T.Normalize((0.485, 0.456, 0.406), (0.229, 0.224, 0.225))
  ])

  image = img_transform(image)
  image = image.unsqueeze(0)
  return image
2个回答

4
这里使用unsqueeze可能是因为您正在使用卷积神经网络。
当您加载图像时,它通常会有3个维度,宽度、高度和颜色通道数。对于黑白图像,颜色通道数为1,对于彩色图像,有3个颜色通道(红、绿、蓝,RGB)。因此,在您的情况下,当您加载图像并将其存储为张量时,它具有以下形状:
image = img_transform(image) # the resulting image has shape [3, H, W]

注意,维度顺序为[通道数,高度,宽度]而不是其他顺序的原因是因为PyTorch。其他库/软件可能会有不同的处理方式。
然而,对于2D卷积神经网络来说,3个维度是不够的。在深度学习中,数据是批次处理的。所以,在卷积神经网络的情况下,它不仅仅是单张图片的处理,而是同时并行处理N张图片。我们将这些图片的集合称为“批次”。因此,维度不再是[C, H, W],而是[N, C, H, W](如此处所示)。例如,对于一个包含64张大小为100x100的彩色图像的批次,你将拥有以下形状:
[64, 3, 100, 100]

现在,如果您只想一次处理一张图片,仍然需要将其转换为批处理形式以便模型接受。例如,如果您有一个形状为[3, 100, 100]的图像,您需要将其转换为[1, 3, 100, 100]。这就是unsqueeze(0)的作用:

image = img_transform(image) # [3, H, W]
image = image.unsqueeze(0) # [1, 3, H, W]

感谢Jay提供了一个好的答案......继续帮助Jay......再次感谢你。 - Rachit S Garg

0
在这行代码之后:
image = Image.open(img_path).convert('RGB')

image 可能是一个三维矩阵。一种可能的布局方式是使用尺寸 [通道,行,强度]

  • R 矩阵包含许多行,每行包含了红色通道的强度值;
  • G 矩阵包含许多行,每行包含了绿色通道的强度值;
  • B 矩阵包含许多行,每行包含了蓝色通道的强度值。

在机器学习中,当我们在训练模型时,很少只关心一个例子。我们会训练一批样本。一个批次就是简单地将图像叠加在彼此上方,因此我们需要从 [通道,行,强度] 转换为 [批次,通道,行,强度]

这就是 unsqueeze(0) 的作用,它添加了一个新的零维度,用于使图像可堆叠。


1
PyTorch使用[N,C,H,W]约定来表示图像的维度,其中N =批量大小,C =颜色通道,H =高度,W =宽度。你理论上可以给它任何东西,但通常这是图像处理的约定。 - Jay Mody
1
感谢Richard的帮助。非常感谢。 - Rachit S Garg

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接