昇思学习打卡-8-计算机视觉/FCN图像语义分割

FCN介绍

FCN主要用于图像分割领域,是一种端到端的分割方法,是深度学习应用在图像语义分割的开山之作。通过进行像素级的预测直接得出与原图大小相等的label map。因FCN丢弃全连接层替换为全卷积层,网络所有层均为卷积层,故称为全卷积网络。

FCN所用的技术

全卷积神经网络主要使用以下三种技术:

  • 卷积化(Convolutional)
  • 上采样(Upsample)
  • 跳跃结构(Skip Layer)
    跳跃结构利用上采样技巧对最后一层的特征图进行上采样,得到原图大小的分割是步长为32像素的预测,称之为FCN-32s。由于最后一层的特征图太小,损失过多细节,采用skips结构将更具有全局信息的最后一层预测和更浅层的预测结合,使预测结果获取更多的局部细节。将底层(stride 32)的预测(FCN-32s)进行2倍的上采样得到原尺寸的图像,并与从pool4层(stride 16)进行的预测融合起来(相加),这一部分的网络被称为FCN-16s。随后将这一部分的预测再进行一次2倍的上采样并与从pool3层得到的预测融合起来,这一部分的网络被称为FCN-8s。 Skips结构将深层的全局信息与浅层的局部信息相结合。

训练数据的可视化

import numpy as np
import matplotlib.pyplot as plt

plt.figure(figsize=(16, 8))

# 对训练集中的数据进行展示
for i in range(1, 9):
    plt.subplot(2, 4, i)
    show_data = next(dataset.create_dict_iterator())
    show_images = show_data["data"].asnumpy()
    show_images = np.clip(show_images, 0, 1)
# 将图片转换HWC格式后进行展示
    plt.imshow(show_images[0].transpose(1, 2, 0))
    plt.axis("off")
    plt.subplots_adjust(wspace=0.05, hspace=0)
plt.show()

在这里插入图片描述

模型训练

import mindspore
from mindspore import Tensor
import mindspore.nn as nn
from mindspore.train import ModelCheckpoint, CheckpointConfig, LossMonitor, TimeMonitor, Model

device_target = "Ascend"
mindspore.set_context(mode=mindspore.PYNATIVE_MODE, device_target=device_target)

train_batch_size = 4
num_classes = 21
# 初始化模型结构
net = FCN8s(n_class=21)
# 导入vgg16预训练参数
load_vgg16()
# 计算学习率
min_lr = 0.0005
base_lr = 0.05
train_epochs = 1
iters_per_epoch = dataset.get_dataset_size()
total_step = iters_per_epoch * train_epochs

lr_scheduler = mindspore.nn.cosine_decay_lr(min_lr,
                                            base_lr,
                                            total_step,
                                            iters_per_epoch,
                                            decay_epoch=2)
lr = Tensor(lr_scheduler[-1])

# 定义损失函数
loss = nn.CrossEntropyLoss(ignore_index=255)
# 定义优化器
optimizer = nn.Momentum(params=net.trainable_params(), learning_rate=lr, momentum=0.9, weight_decay=0.0001)
# 定义loss_scale
scale_factor = 4
scale_window = 3000
loss_scale_manager = ms.amp.DynamicLossScaleManager(scale_factor, scale_window)
# 初始化模型
if device_target == "Ascend":
    model = Model(net, loss_fn=loss, optimizer=optimizer, loss_scale_manager=loss_scale_manager, metrics={"pixel accuracy": PixelAccuracy(), "mean pixel accuracy": PixelAccuracyClass(), "mean IoU": MeanIntersectionOverUnion(), "frequency weighted IoU": FrequencyWeightedIntersectionOverUnion()})
else:
    model = Model(net, loss_fn=loss, optimizer=optimizer, metrics={"pixel accuracy": PixelAccuracy(), "mean pixel accuracy": PixelAccuracyClass(), "mean IoU": MeanIntersectionOverUnion(), "frequency weighted IoU": FrequencyWeightedIntersectionOverUnion()})

# 设置ckpt文件保存的参数
time_callback = TimeMonitor(data_size=iters_per_epoch)
loss_callback = LossMonitor()
callbacks = [time_callback, loss_callback]
save_steps = 330
keep_checkpoint_max = 5
config_ckpt = CheckpointConfig(save_checkpoint_steps=10,
                               keep_checkpoint_max=keep_checkpoint_max)
ckpt_callback = ModelCheckpoint(prefix="FCN8s",
                                directory="./ckpt",
                                config=config_ckpt)
callbacks.append(ckpt_callback)
model.train(train_epochs, dataset, callbacks=callbacks)

在这里插入图片描述

模型推理

import cv2
import matplotlib.pyplot as plt

net = FCN8s(n_class=num_classes)
# 设置超参
ckpt_file = "FCN8s.ckpt"
param_dict = load_checkpoint(ckpt_file)
load_param_into_net(net, param_dict)
eval_batch_size = 4
img_lst = []
mask_lst = []
res_lst = []
# 推理效果展示(上方为输入图片,下方为推理效果图片)
plt.figure(figsize=(8, 5))
show_data = next(dataset_eval.create_dict_iterator())
show_images = show_data["data"].asnumpy()
mask_images = show_data["label"].reshape([4, 512, 512])
show_images = np.clip(show_images, 0, 1)
for i in range(eval_batch_size):
    img_lst.append(show_images[i])
    mask_lst.append(mask_images[i])
res = net(show_data["data"]).asnumpy().argmax(axis=1)
for i in range(eval_batch_size):
    plt.subplot(2, 4, i + 1)
    plt.imshow(img_lst[i].transpose(1, 2, 0))
    plt.axis("off")
    plt.subplots_adjust(wspace=0.05, hspace=0.02)
    plt.subplot(2, 4, i + 5)
    plt.imshow(res[i])
    plt.axis("off")
    plt.subplots_adjust(wspace=0.05, hspace=0.02)
plt.show()

在这里插入图片描述

FCN的优点和不足

除了文中提到的FCN的优缺点,我还了解到以下优缺点:

优点

  • 端到端的像素级分类:FCN能够实现从图像到像素级的端到端语义分割。
  • 保留空间信息:FCN通过卷积层和上采样操作保留了图像的重要空间信息,有助于提高分割精度。
  • 鲁棒性:FCN对图像的旋转、平移等变化具有较强的鲁棒性。
  • 广泛性:FCN适用于各种类型的图像分割任务,包括彩色图像、灰度图像和多光谱图像等。

不足

  • 训练复杂性:FCN可能需要多次训练和微调才能获得较好的性能,例如FCN-32s、FCN-16s和FCN-8s的逐步训练。
  • 计算量大:FCN需要进行大量的卷积运算和参数学习,导致计算量大,训练时间长。
  • 对噪声敏感:FCN可能对噪声和图像中的无关信息较为敏感,容易受到干扰。
  • 数据需求量大:FCN的训练通常需要大量的标注数据,这在某些领域可能是一个挑战。

此章节学习到此结束,感谢昇思平台。

最近更新

  1. docker php8.1+nginx base 镜像 dockerfile 配置

    2024-07-12 08:50:03       67 阅读
  2. Could not load dynamic library ‘cudart64_100.dll‘

    2024-07-12 08:50:03       72 阅读
  3. 在Django里面运行非项目文件

    2024-07-12 08:50:03       58 阅读
  4. Python语言-面向对象

    2024-07-12 08:50:03       69 阅读

热门阅读

  1. 时间复杂度

    2024-07-12 08:50:03       27 阅读
  2. 735. 小行星碰撞

    2024-07-12 08:50:03       29 阅读
  3. HTTP3.0

    2024-07-12 08:50:03       23 阅读
  4. notes for datawhale 2th summer camp NLP task1

    2024-07-12 08:50:03       26 阅读
  5. 配置 Node.js 内存限制

    2024-07-12 08:50:03       23 阅读
  6. tomcat的安装和解析

    2024-07-12 08:50:03       25 阅读
  7. Sentieon应用教程:本地使用-Quick_start

    2024-07-12 08:50:03       26 阅读
  8. Django ORM中的Q对象

    2024-07-12 08:50:03       26 阅读
  9. 基于python实现并编译提升cpu与内存使用率的脚本

    2024-07-12 08:50:03       24 阅读
  10. C-MAPSS数据集-RUL剩余寿命预测

    2024-07-12 08:50:03       24 阅读
  11. Linux workqueue介绍

    2024-07-12 08:50:03       20 阅读
  12. C++异常处理throw try catch

    2024-07-12 08:50:03       24 阅读