目录
- import torch
- from torch import nn
-
- input = torch.tensor([[[1, 2, 0, 3, 1],
- [0, 1, 2, 3, 1],
- [1, 2, 1, 0, 0],
- [5, 2, 3, 1, 1],
- [2, 1, 0, 1, 1]],
- [[1, 2, 0, 3, 1],
- [0, 1, 2, 3, 1],
- [1, 2, 1, 0, 0],
- [5, 2, 3, 1, 1],
- [2, 1, 0, 1, 1]],
- [[1, 2, 0, 3, 1],
- [0, 1, 2, 3, 1],
- [1, 2, 1, 0, 0],
- [5, 2, 3, 1, 1],
- [2, 1, 0, 1, 1]]], dtype=torch.float32)
- print(input.shape)
- input = torch.reshape(input, (-1, 3, 5, 5))
- print(input.shape)
-
-
- class ZiDingYi(nn.Module):
- def __init__(self):
- super(ZiDingYi, self).__init__()
- self.conv1 = nn.Conv2d(in_channels=3, out_channels=6, kernel_size=3, stride=(1, 1), padding=0)
-
- def forward(self, x):
- x = self.conv1(x)
- return x
-
-
- zidingyi = ZiDingYi()
- print(zidingyi)
-
- output = zidingyi(input)
- print(output)
自创一个tensor张量,为了与图像相符合,采用了三通道、高与宽的形式。
- input = torch.tensor([[[1, 2, 0, 3, 1],
- [0, 1, 2, 3, 1],
- [1, 2, 1, 0, 0],
- [5, 2, 3, 1, 1],
- [2, 1, 0, 1, 1]],
- [[1, 2, 0, 3, 1],
- [0, 1, 2, 3, 1],
- [1, 2, 1, 0, 0],
- [5, 2, 3, 1, 1],
- [2, 1, 0, 1, 1]],
- [[1, 2, 0, 3, 1],
- [0, 1, 2, 3, 1],
- [1, 2, 1, 0, 0],
- [5, 2, 3, 1, 1],
- [2, 1, 0, 1, 1]]], dtype=torch.float32)
- print(input.shape)
- input = torch.reshape(input, (-1, 3, 5, 5))
- print(input.shape)
注意的点1:
输入的整数系统默认识别为长整型(long),这种数据类型神经网络不能接收,必须强制转换为浮点型,其中torch下给出了浮点型的数据类型。
dtype=torch.float32
注意的点2:
不知道新增维度的值时可以给-1让系统自己运算。
input = torch.reshape(input, (-1, 3, 5, 5))
继承nn.Module父类,利用super()调用父类中的__init__()
- class ZiDingYi(nn.Module):
- def __init__(self):
- super(ZiDingYi, self).__init__()
- self.conv1 = nn.Conv2d(in_channels=3, out_channels=6, kernel_size=3, stride=(1, 1), padding=0)
-
- def forward(self, x):
- x = self.conv1(x)
- return x
其中2d卷积的参数,收到的通道数,输出的通道数,卷积核大小(可以给int,也可以给元组,此处给的int),步长(可以给int,也可以给元组,此处给的元组),填充大小。
forward()函数负责利用__init__()的属性,传入输入值并返回输出值。
结果:
- torch.Size([3, 5, 5])
- torch.Size([1, 3, 5, 5])
- ZiDingYi(
- (conv1): Conv2d(3, 6, kernel_size=(3, 3), stride=(1, 1))
- )
- tensor([[[[ 0.7182, 2.4224, 0.9817],
- [ 1.7839, 2.5734, 1.2106],
- [ 1.8459, 1.5189, 1.4425]],
-
- [[ 0.1448, -0.0430, 0.0554],
- [-0.7607, -0.3164, -1.1233],
- [ 0.9714, 0.2079, 1.0055]],
-
- [[-0.4258, -0.7102, -0.6917],
- [-0.3210, -0.1598, -0.8339],
- [-2.5572, -1.2985, -1.3247]],
-
- [[ 0.4376, -0.4646, -1.1285],
- [ 0.1640, 0.0108, 0.2103],
- [-0.5246, -0.5199, 0.1915]],
-
- [[ 1.2390, 1.2742, 1.0452],
- [ 0.5466, 0.6744, 1.8741],
- [-0.0987, -0.1915, -1.2585]],
-
- [[-0.7630, 0.5245, -0.3805],
- [-0.2918, 0.1074, -0.2167],
- [ 0.1180, 0.4456, 0.2908]]]], grad_fn=
) -
- Process finished with exit code 0
观察结果符合特征图大小计算公式:
输出高=((输入高+2×填充大小-卷积核大小)/步长大小)+1
- import torch
- import torchvision
- from torch import nn
- from torch.utils.data import DataLoader
-
- input = torch.tensor([[[1, 2, 0, 3, 1],
- [0, 1, 2, 3, 1],
- [1, 2, 1, 0, 0],
- [5, 2, 3, 1, 1],
- [2, 1, 0, 1, 1]],
- [[1, 2, 0, 3, 1],
- [0, 1, 2, 3, 1],
- [1, 2, 1, 0, 0],
- [5, 2, 3, 1, 1],
- [2, 1, 0, 1, 1]],
- [[1, 2, 0, 3, 1],
- [0, 1, 2, 3, 1],
- [1, 2, 1, 0, 0],
- [5, 2, 3, 1, 1],
- [2, 1, 0, 1, 1]]], dtype=torch.float32)
- print(input.shape)
- input = torch.reshape(input, (-1, 3, 5, 5))
- print(input.shape)
-
-
- class ZiDingYi(nn.Module):
- def __init__(self):
- super(ZiDingYi, self).__init__()
- self.conv1 = nn.Conv2d(in_channels=3, out_channels=6, kernel_size=3, stride=(1, 1), padding=0)
-
- def forward(self, x):
- x = self.conv1(x)
- return x
-
-
- zidingyi = ZiDingYi()
- print(zidingyi)
-
- output = zidingyi(input)
- print(output)
-
- dataset_transforms = torchvision.transforms.Compose([torchvision.transforms.ToTensor(),
- torchvision.transforms.Normalize((0.4915, 0.4823, 0.4468),
- (0.2470, 0.2435, 0.2616))])
- train_dataset = torchvision.datasets.CIFAR10(root="./dataset", train=True, download=True, transform=dataset_transforms)
- train_dataloader = DataLoader(dataset=train_dataset, batch_size=64, shuffle=True, num_workers=0, drop_last=False)
-
- for data in train_dataloader:
- imgs, labels = data
- output2 = zidingyi(imgs)
- print(imgs.shape)
- print(output2.shape)
结果:
- torch.Size([3, 5, 5])
- torch.Size([1, 3, 5, 5])
- ZiDingYi(
- (conv1): Conv2d(3, 6, kernel_size=(3, 3), stride=(1, 1))
- )
- tensor([[[[-0.3747, 1.3237, -0.4478],
- [ 0.7121, 1.4943, 0.4299],
- [ 0.4241, -0.6195, -0.0987]],
-
- [[-0.7136, -1.2816, -1.1319],
- [-1.2081, -1.2827, -0.4157],
- [-0.6310, -0.6770, -0.0811]],
-
- [[-0.8652, 0.0879, -0.4910],
- [-1.2453, 0.2760, 0.0546],
- [-0.8033, -0.5222, -0.3930]],
-
- [[-0.1145, 0.3100, -0.8689],
- [ 1.0125, 0.6360, -0.2982],
- [-0.6484, -1.0439, -0.3103]],
-
- [[-0.3132, -0.5373, -1.3907],
- [ 0.4211, -1.0112, -0.5164],
- [-1.5543, -0.2601, -0.3318]],
-
- [[-0.4129, -1.6505, -0.0648],
- [ 0.1058, 0.1305, 0.3511],
- [ 0.6991, -0.3641, 0.6684]]]], grad_fn=
) - Files already downloaded and verified
- torch.Size([64, 3, 32, 32])
- torch.Size([64, 6, 30, 30])
- torch.Size([64, 3, 32, 32])
- torch.Size([64, 6, 30, 30])
- torch.Size([64, 3, 32, 32])
- torch.Size([64, 6, 30, 30])
- torch.Size([64, 3, 32, 32])
- torch.Size([64, 6, 30, 30])
- ————————————后面省略——————————————
其中64为批处理大小,通道数由3转化为6,特征图从32高宽转为30高宽,符合计算公式。
- torch.Size([64, 3, 32, 32])
- torch.Size([64, 6, 30, 30])
- import torch
- import torchvision
- from torch import nn
- from torch.utils.data import DataLoader
- from torch.utils.tensorboard import SummaryWriter
-
- input = torch.tensor([[[1, 2, 0, 3, 1],
- [0, 1, 2, 3, 1],
- [1, 2, 1, 0, 0],
- [5, 2, 3, 1, 1],
- [2, 1, 0, 1, 1]],
- [[1, 2, 0, 3, 1],
- [0, 1, 2, 3, 1],
- [1, 2, 1, 0, 0],
- [5, 2, 3, 1, 1],
- [2, 1, 0, 1, 1]],
- [[1, 2, 0, 3, 1],
- [0, 1, 2, 3, 1],
- [1, 2, 1, 0, 0],
- [5, 2, 3, 1, 1],
- [2, 1, 0, 1, 1]]], dtype=torch.float32)
- print(input.shape)
- input = torch.reshape(input, (-1, 3, 5, 5))
- print(input.shape)
-
-
- class ZiDingYi(nn.Module):
- def __init__(self):
- super(ZiDingYi, self).__init__()
- self.conv1 = nn.Conv2d(in_channels=3, out_channels=6, kernel_size=3, stride=(1, 1), padding=0)
-
- def forward(self, x):
- x = self.conv1(x)
- return x
-
-
- zidingyi = ZiDingYi()
- print(zidingyi)
-
- output = zidingyi(input)
- print(output)
-
- dataset_transforms = torchvision.transforms.Compose([torchvision.transforms.ToTensor(),
- torchvision.transforms.Normalize((0.4915, 0.4823, 0.4468),
- (0.2470, 0.2435, 0.2616))])
- train_dataset = torchvision.datasets.CIFAR10(root="./dataset", train=True, download=True, transform=dataset_transforms)
- train_dataloader = DataLoader(dataset=train_dataset, batch_size=64, shuffle=True, num_workers=0, drop_last=False)
-
- writer = SummaryWriter("./logs")
- step = 0
- for data in train_dataloader:
- imgs, labels = data
- output2 = zidingyi(imgs)
- print(imgs.shape)
- # torch.Size([64, 3, 32, 32])
- print(output2.shape)
- # torch.Size([64, 6, 30, 30])
- # 这个是显示不出来的,需要reshape一下,转化为3通道
- writer.add_images(tag="input", img_tensor=imgs, global_step=step)
- output_reshape = torch.reshape(output2, (-1, 3, 30, 30))
- writer.add_images(tag="output", img_tensor=output_reshape, global_step=step)
- step += 1
- writer.close()
进入Terminal终端
tensorboard --logdir=logs
- (pytorch) D:\project\pytorch_learn>tensorboard --logdir=logs
- TensorFlow installation not found - running with reduced feature set.
- Serving TensorBoard on localhost; to expose to the network, use a proxy or pass --bind_all
- TensorBoard 2.10.1 at http://localhost:6006/ (Press CTRL+C to quit)
input是归一化后的图片,归一化后灰度值会有负数,显示的时候负数置0,变黑色。
output是卷积处理后的图片,每个卷积核可以视为一个滤波器。
其中同一行会有两个形状的图片,那是因为一个图片三个通道,经过卷积操作变成了6个通道,但是由于图片只能三个通道的时候显示出来(为了在tensorboard上观察),故进行了reshape操作:
output_reshape = torch.reshape(output2, (-1, 3, 30, 30))
(64,6,30,30)reshape成了(128,3,30,30)
6通道变成了两个3通道,由两个图片显示出来。