• 3.pytorch学习:conv2d——2d卷积


    目录

    自建一个tensor理解卷积

    加入图像数据集

    tensorboard查看卷积后的图片


    自建一个tensor理解卷积

    1. import torch
    2. from torch import nn
    3. input = torch.tensor([[[1, 2, 0, 3, 1],
    4. [0, 1, 2, 3, 1],
    5. [1, 2, 1, 0, 0],
    6. [5, 2, 3, 1, 1],
    7. [2, 1, 0, 1, 1]],
    8. [[1, 2, 0, 3, 1],
    9. [0, 1, 2, 3, 1],
    10. [1, 2, 1, 0, 0],
    11. [5, 2, 3, 1, 1],
    12. [2, 1, 0, 1, 1]],
    13. [[1, 2, 0, 3, 1],
    14. [0, 1, 2, 3, 1],
    15. [1, 2, 1, 0, 0],
    16. [5, 2, 3, 1, 1],
    17. [2, 1, 0, 1, 1]]], dtype=torch.float32)
    18. print(input.shape)
    19. input = torch.reshape(input, (-1, 3, 5, 5))
    20. print(input.shape)
    21. class ZiDingYi(nn.Module):
    22. def __init__(self):
    23. super(ZiDingYi, self).__init__()
    24. self.conv1 = nn.Conv2d(in_channels=3, out_channels=6, kernel_size=3, stride=(1, 1), padding=0)
    25. def forward(self, x):
    26. x = self.conv1(x)
    27. return x
    28. zidingyi = ZiDingYi()
    29. print(zidingyi)
    30. output = zidingyi(input)
    31. print(output)

    自创一个tensor张量,为了与图像相符合,采用了三通道、高与宽的形式。

    1. input = torch.tensor([[[1, 2, 0, 3, 1],
    2. [0, 1, 2, 3, 1],
    3. [1, 2, 1, 0, 0],
    4. [5, 2, 3, 1, 1],
    5. [2, 1, 0, 1, 1]],
    6. [[1, 2, 0, 3, 1],
    7. [0, 1, 2, 3, 1],
    8. [1, 2, 1, 0, 0],
    9. [5, 2, 3, 1, 1],
    10. [2, 1, 0, 1, 1]],
    11. [[1, 2, 0, 3, 1],
    12. [0, 1, 2, 3, 1],
    13. [1, 2, 1, 0, 0],
    14. [5, 2, 3, 1, 1],
    15. [2, 1, 0, 1, 1]]], dtype=torch.float32)
    16. print(input.shape)
    17. input = torch.reshape(input, (-1, 3, 5, 5))
    18. print(input.shape)

    注意的点1:

    输入的整数系统默认识别为长整型(long),这种数据类型神经网络不能接收,必须强制转换为浮点型,其中torch下给出了浮点型的数据类型。

    dtype=torch.float32

    注意的点2:

    不知道新增维度的值时可以给-1让系统自己运算。

    input = torch.reshape(input, (-1, 3, 5, 5))

     继承nn.Module父类,利用super()调用父类中的__init__()

    1. class ZiDingYi(nn.Module):
    2. def __init__(self):
    3. super(ZiDingYi, self).__init__()
    4. self.conv1 = nn.Conv2d(in_channels=3, out_channels=6, kernel_size=3, stride=(1, 1), padding=0)
    5. def forward(self, x):
    6. x = self.conv1(x)
    7. return x

    其中2d卷积的参数,收到的通道数,输出的通道数,卷积核大小(可以给int,也可以给元组,此处给的int),步长(可以给int,也可以给元组,此处给的元组),填充大小。

    forward()函数负责利用__init__()的属性,传入输入值并返回输出值。

    结果:

    1. torch.Size([3, 5, 5])
    2. torch.Size([1, 3, 5, 5])
    3. ZiDingYi(
    4. (conv1): Conv2d(3, 6, kernel_size=(3, 3), stride=(1, 1))
    5. )
    6. tensor([[[[ 0.7182, 2.4224, 0.9817],
    7. [ 1.7839, 2.5734, 1.2106],
    8. [ 1.8459, 1.5189, 1.4425]],
    9. [[ 0.1448, -0.0430, 0.0554],
    10. [-0.7607, -0.3164, -1.1233],
    11. [ 0.9714, 0.2079, 1.0055]],
    12. [[-0.4258, -0.7102, -0.6917],
    13. [-0.3210, -0.1598, -0.8339],
    14. [-2.5572, -1.2985, -1.3247]],
    15. [[ 0.4376, -0.4646, -1.1285],
    16. [ 0.1640, 0.0108, 0.2103],
    17. [-0.5246, -0.5199, 0.1915]],
    18. [[ 1.2390, 1.2742, 1.0452],
    19. [ 0.5466, 0.6744, 1.8741],
    20. [-0.0987, -0.1915, -1.2585]],
    21. [[-0.7630, 0.5245, -0.3805],
    22. [-0.2918, 0.1074, -0.2167],
    23. [ 0.1180, 0.4456, 0.2908]]]], grad_fn=)
    24. Process finished with exit code 0

    观察结果符合特征图大小计算公式:

    输出高=((输入高+2×填充大小-卷积核大小)/步长大小)+1

    加入图像数据集

    1. import torch
    2. import torchvision
    3. from torch import nn
    4. from torch.utils.data import DataLoader
    5. input = torch.tensor([[[1, 2, 0, 3, 1],
    6. [0, 1, 2, 3, 1],
    7. [1, 2, 1, 0, 0],
    8. [5, 2, 3, 1, 1],
    9. [2, 1, 0, 1, 1]],
    10. [[1, 2, 0, 3, 1],
    11. [0, 1, 2, 3, 1],
    12. [1, 2, 1, 0, 0],
    13. [5, 2, 3, 1, 1],
    14. [2, 1, 0, 1, 1]],
    15. [[1, 2, 0, 3, 1],
    16. [0, 1, 2, 3, 1],
    17. [1, 2, 1, 0, 0],
    18. [5, 2, 3, 1, 1],
    19. [2, 1, 0, 1, 1]]], dtype=torch.float32)
    20. print(input.shape)
    21. input = torch.reshape(input, (-1, 3, 5, 5))
    22. print(input.shape)
    23. class ZiDingYi(nn.Module):
    24. def __init__(self):
    25. super(ZiDingYi, self).__init__()
    26. self.conv1 = nn.Conv2d(in_channels=3, out_channels=6, kernel_size=3, stride=(1, 1), padding=0)
    27. def forward(self, x):
    28. x = self.conv1(x)
    29. return x
    30. zidingyi = ZiDingYi()
    31. print(zidingyi)
    32. output = zidingyi(input)
    33. print(output)
    34. dataset_transforms = torchvision.transforms.Compose([torchvision.transforms.ToTensor(),
    35. torchvision.transforms.Normalize((0.4915, 0.4823, 0.4468),
    36. (0.2470, 0.2435, 0.2616))])
    37. train_dataset = torchvision.datasets.CIFAR10(root="./dataset", train=True, download=True, transform=dataset_transforms)
    38. train_dataloader = DataLoader(dataset=train_dataset, batch_size=64, shuffle=True, num_workers=0, drop_last=False)
    39. for data in train_dataloader:
    40. imgs, labels = data
    41. output2 = zidingyi(imgs)
    42. print(imgs.shape)
    43. print(output2.shape)

    结果:

    1. torch.Size([3, 5, 5])
    2. torch.Size([1, 3, 5, 5])
    3. ZiDingYi(
    4. (conv1): Conv2d(3, 6, kernel_size=(3, 3), stride=(1, 1))
    5. )
    6. tensor([[[[-0.3747, 1.3237, -0.4478],
    7. [ 0.7121, 1.4943, 0.4299],
    8. [ 0.4241, -0.6195, -0.0987]],
    9. [[-0.7136, -1.2816, -1.1319],
    10. [-1.2081, -1.2827, -0.4157],
    11. [-0.6310, -0.6770, -0.0811]],
    12. [[-0.8652, 0.0879, -0.4910],
    13. [-1.2453, 0.2760, 0.0546],
    14. [-0.8033, -0.5222, -0.3930]],
    15. [[-0.1145, 0.3100, -0.8689],
    16. [ 1.0125, 0.6360, -0.2982],
    17. [-0.6484, -1.0439, -0.3103]],
    18. [[-0.3132, -0.5373, -1.3907],
    19. [ 0.4211, -1.0112, -0.5164],
    20. [-1.5543, -0.2601, -0.3318]],
    21. [[-0.4129, -1.6505, -0.0648],
    22. [ 0.1058, 0.1305, 0.3511],
    23. [ 0.6991, -0.3641, 0.6684]]]], grad_fn=)
    24. Files already downloaded and verified
    25. torch.Size([64, 3, 32, 32])
    26. torch.Size([64, 6, 30, 30])
    27. torch.Size([64, 3, 32, 32])
    28. torch.Size([64, 6, 30, 30])
    29. torch.Size([64, 3, 32, 32])
    30. torch.Size([64, 6, 30, 30])
    31. torch.Size([64, 3, 32, 32])
    32. torch.Size([64, 6, 30, 30])
    33. ————————————后面省略——————————————

     其中64为批处理大小,通道数由3转化为6,特征图从32高宽转为30高宽,符合计算公式。

    1. torch.Size([64, 3, 32, 32])
    2. torch.Size([64, 6, 30, 30])

    tensorboard查看卷积后的图片

    1. import torch
    2. import torchvision
    3. from torch import nn
    4. from torch.utils.data import DataLoader
    5. from torch.utils.tensorboard import SummaryWriter
    6. input = torch.tensor([[[1, 2, 0, 3, 1],
    7. [0, 1, 2, 3, 1],
    8. [1, 2, 1, 0, 0],
    9. [5, 2, 3, 1, 1],
    10. [2, 1, 0, 1, 1]],
    11. [[1, 2, 0, 3, 1],
    12. [0, 1, 2, 3, 1],
    13. [1, 2, 1, 0, 0],
    14. [5, 2, 3, 1, 1],
    15. [2, 1, 0, 1, 1]],
    16. [[1, 2, 0, 3, 1],
    17. [0, 1, 2, 3, 1],
    18. [1, 2, 1, 0, 0],
    19. [5, 2, 3, 1, 1],
    20. [2, 1, 0, 1, 1]]], dtype=torch.float32)
    21. print(input.shape)
    22. input = torch.reshape(input, (-1, 3, 5, 5))
    23. print(input.shape)
    24. class ZiDingYi(nn.Module):
    25. def __init__(self):
    26. super(ZiDingYi, self).__init__()
    27. self.conv1 = nn.Conv2d(in_channels=3, out_channels=6, kernel_size=3, stride=(1, 1), padding=0)
    28. def forward(self, x):
    29. x = self.conv1(x)
    30. return x
    31. zidingyi = ZiDingYi()
    32. print(zidingyi)
    33. output = zidingyi(input)
    34. print(output)
    35. dataset_transforms = torchvision.transforms.Compose([torchvision.transforms.ToTensor(),
    36. torchvision.transforms.Normalize((0.4915, 0.4823, 0.4468),
    37. (0.2470, 0.2435, 0.2616))])
    38. train_dataset = torchvision.datasets.CIFAR10(root="./dataset", train=True, download=True, transform=dataset_transforms)
    39. train_dataloader = DataLoader(dataset=train_dataset, batch_size=64, shuffle=True, num_workers=0, drop_last=False)
    40. writer = SummaryWriter("./logs")
    41. step = 0
    42. for data in train_dataloader:
    43. imgs, labels = data
    44. output2 = zidingyi(imgs)
    45. print(imgs.shape)
    46. # torch.Size([64, 3, 32, 32])
    47. print(output2.shape)
    48. # torch.Size([64, 6, 30, 30])
    49. # 这个是显示不出来的,需要reshape一下,转化为3通道
    50. writer.add_images(tag="input", img_tensor=imgs, global_step=step)
    51. output_reshape = torch.reshape(output2, (-1, 3, 30, 30))
    52. writer.add_images(tag="output", img_tensor=output_reshape, global_step=step)
    53. step += 1
    54. writer.close()

    进入Terminal终端

    tensorboard --logdir=logs
    
    1. (pytorch) D:\project\pytorch_learn>tensorboard --logdir=logs
    2. TensorFlow installation not found - running with reduced feature set.
    3. Serving TensorBoard on localhost; to expose to the network, use a proxy or pass --bind_all
    4. 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通道,由两个图片显示出来。

  • 相关阅读:
    S7-200 SMART与ABB ACS580变频器进行MODBUS RTU通信的具体方法示例
    优先级队列(堆)【Java】
    C++算法:二叉树的序列化与反序列化
    初探工厂抽象模式
    简单聊聊 分布式
    C. String Transformation 1(图的思想)
    easy-monitor3.0 nodejs性能监控和分析工具
    IDEA中 lombok不生效解决方法
    win下的开发环境变量记录
    《信息学奥赛一本通·初赛真题解析》
  • 原文地址:https://blog.csdn.net/wzfafabga/article/details/127695823