CMake 入门

官方教程

构建基础 CMake 项目

01 CMake 最基本组成

一个基础项目由 CMakeLists.txt 文件包含三句命令组成

目录结构

1
2
3
- Help/guide/tutorial/Step1
- tutorial.cxx
- CMakeLists.txt

CMakelists.txt

1
2
3
4
5
6
# 1(必须)- 项目顶部指定最低可用CMake版本
cmake_minimum_required(VERSION 3.10)
# 2(必须)- 指定项目名、语言及版本号等,必须在CMake版本声明之后
project(Tutorial)
# 3(必须)- 告知CMake用于生成可执行程序的源代码文件
add_executable(Tutorial tutorial.cxx)

02 CMAKE_开头变量

通常以 CMAKE_开头的变量在 CMake 中有特殊含义,如CMAKE_CXX_STANDARDCMAKE_CXX_STANDARD_REQUIRED配合使用可以用于指定 C++标准,可以通过set()命令定义变量

CMakelists.txt

1
2
3
# 指定使用 C++11 标准
set(CMAKE_CXX_STANDARD 11)
set(CMAKE_CXX_STANDARD_REQUIRED True)

03 使用配置头文件

当我们需要 CMakelists.txt 中定义的变量在源代码中可见,可以通过配置头文件实现 通过configure_file()命令替换输入文件中的由 CMakelists.txt 定义的变量值,然后复制到输出文件中

CMakelists.txt

1
2
3
4
5
6
7
8
# 执行 project() 命令时,CMake 自动定义 Tutorial_VERSION_MAJOR 变量 和 Tutorial_VERSION_MINOR 变量
project(Tutorial VERSION 1.0)
# TutorialConfig.h.in 作为输入配置头文件,变量 @Tutorial_VERSION_MAJOR@ 和 @Tutorial_VERSION_MINOR@ 在 TutorialConfig.h 中将会被替换
configure_file(TutorialConfig.h.in TutorialConfig.h)
# 配置文件将输出到${PROJECT_BINARY_DIR}目录,添加该目录用于让CMake搜寻需要include的文件
target_include_directories(Tutorial PUBLIC
"${PROJECT_BINARY_DIR}"
)

TutorialConfig.h.in

1
2
3
// Tutorial 项目配置
#define Tutorial_VERSION_MAJOR @Tutorial_VERSION_MAJOR@
#define Tutorial_VERSION_MINOR @Tutorial_VERSION_MINOR@

tutorial.cxx

1
2
3
4
5
6
7
8
9
#include "TutorialConfig.h"

if (argc < 2) {
// 输出项目版本
std::cout << argv[0] << " Version " << Tutorial_VERSION_MAJOR << "."
<< Tutorial_VERSION_MINOR << std::endl;
std::cout << "Usage: " << argv[0] << " number" << std::endl;
return 1;
}

添加库文件

01 创建一个库

  • 通过add_library()命令添加库,并指定组成该库的源文件
  • 通过add_subdirectory()命令添加子目录用于构建项目
  • 通过target_include_directories()target_link_libraries()命令链接到可执行目标

目录结构

1
2
3
4
5
6
7
8
9
10
11
- Help/guide/tutorial/Step2
- CMakeLists.txt
- tutorial.cxx
- MathFunctions
- CMakeLists.txt
- MathFunctions.h
- mysqrt.h
- MathFunctions.cxx
[function] sqrt
- mysqrt.cxx
[function] mysqrt

MathFunctions/CMakeLists.txt

1
2
# 创建 MathFunctions 库
add_library(MathFunctions MathFunctions.cxx mysqrt.cxx)

CMakeLists.txt

1
2
3
4
5
6
7
8
9
# 使用 MathFunctions 库
add_subdirectory(MathFunctions)
# 链接库到可执行目标
target_link_libraries(Tutorial PUBLIC MathFunctions)
# 指定库头文件位置,使得 MathFunctions.h 头文件可见
target_include_directories(Tutorial PUBLIC
"${PROJECT_BINARY_DIR}"
"${PROJECT_SOURCE_DIR}/MathFunctions"
)

tutorial.cxx

1
2
#include "MathFunctions.h"
const double outputValue = mathfunctions::sqrt(inputValue);

02 添加 Option

通过 option() 命令为用户提供变量用于配置构建,该配置将会保存在 cache,因此用户不需要每次都设置

MathFunctions/CMakeLists.txt

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
# 相比于之前的配置移除了 mysqrt.cxx 文件,变更为随着 USE_MYMATH 的设置动态链接,减少资源消耗
add_library(MathFunctions MathFunctions.cxx)

# 为用户提供选项 USE_MYMATH,默认为 ON
option(USE_MYMATH "Use tutorial provided math implementation" ON)
# 创建 if() 语句检查 USE_MYMATH 的值
if (USE_MYMATH)
# 设置编译定义 USE_MYMATH,可用于源代码中段的启用和废用
target_compile_definitions(MathFunctions PRIVATE "USE_MYMATH")
# 创建额外的库 SqrtLibrary 负责 mysqrt.cxx 的编译
add_library(SqrtLibrary STATIC
mysqrt.cxx
)
# 链接 SqrtLibrary 库到 MathFunctions
target_link_libraries(MathFunctions PRIVATE SqrtLibrary)
endif()

MathFunctions/MathFunctions.cxx

1
2
3
4
5
6
7
8
9
10
11
12
// 通过 USE_MYMATH 变量判断是否引入头文件
#ifdef USE_MYMATH
# include "mysqrt.h"
#endif
#include <cmath>

// 通过 USE_MYMATH 变量选择使用的 sqrt 方法
#ifdef USE_MYMATH
return detail::mysqrt(x);
#else
return std::sqrt(x);
#endif

p

拓扑排序

课程表

最短工作时长

最短距离

Hono

深度学习

  • 模型轻量化
  • 模型蒸馏方法

编程语言

  • C++ 11 特性
  • C++ 常用 STL、内存
  • C++智能指针

面试经验

语义分割模型研究

1. 介绍一下经典的语义分割模型

  1. FCN (全卷积网络) FCN 是最早的端到端语义分割模型之一,它通过去除全连接层并替换为卷积层来实现任意输入尺寸的图像处理。FCN 利用跳跃连接来结合不同层次的特征图以恢复细节信息。

  2. SegNet SegNet 基于 VGG16 架构,其主要特点是使用了编码器-解码器结构,并且在解码阶段采用了在编码阶段存储的索引来上采样,从而减少了参数量。

  3. UNet UNet 在医学图像分割中特别受欢迎,因为它能够有效地处理小数据集。它包含一个收缩路径(下采样)和一个对称的扩展路径(上采样),并在每个解码步骤中从编码器获取相应的特征图。

  4. DeepLabV3+ DeepLab 系列是谷歌提出的一组模型,它们使用了空洞卷积(又称扩张卷积)来捕捉多尺度信息,并引入了 ASPP 模块来进一步增强模型的多尺度感受野。DeepLabV3+增加了解码模块来恢复分割细节。

  5. HRNet HRNet 专注于在整个网络中保持高分辨率表示,通过并行的流来处理不同分辨率的特征图,并通过交换模块来融合这些特征。这有助于保留更多的细节信息,防止信息损失。

  6. 通道、空间注意力机制 注意力机制(如 SENet 中的通道注意力或 CBAM 中的空间注意力)允许模型专注于重要的特征图区域,同时抑制不相关的背景噪声,提高模型的准确性。

  7. ViT (Vision Transformer) ViT 是一个完全基于 Transformer 架构的视觉模型,它将图像切分为固定大小的补丁,并将这些补丁作为序列传递给标准的 Transformer 编码器。这种设计使得 ViT 可以捕捉全局上下文信息。

  8. SwinFormer SwinFormer 是专门为视觉任务设计的 Transformer 变体,它提出了窗口注意力机制来实现局部和非局部的特征交互,同时保持计算效率。

  9. SegFormer SegFormer 是一个轻量级的分割模型,它结合了 Transformer 编码器(如 MiT)和简单的解码头来实现高效的多尺度特征提取和分割。

  10. SAM (Segment Anything Model) SAM 是一种通用的分割模型,它可以用于任何对象的分割任务而无需特定类别的训练数据。它结合了强大的预训练视觉模型和灵活的提示机制来适应不同的分割需求。

Q: FCN 如何解决不同大小输入的问题? A: FCN 通过移除最后的全连接层,代之以卷积层,允许模型接受任意大小的输入图像,并产生相同大小的分割图。

Q: UNet 如何应对数据不足的情况? A: UNet 的设计包括了一个可以学习到更抽象特征的收缩路径,以及一个可以恢复位置信息的扩展路径,这使得它能够在较少的数据上训练而不会过拟合。

Q: DeepLabV3+中的 ASPP 模块是什么? A: ASPP(Atrous Spatial Pyramid Pooling)模块通过不同 rate 的空洞卷积来捕捉不同尺度的信息,从而增强模型对物体不同大小的适应能力。

Q: ViT 是如何处理图像输入的? A: ViT 首先将输入图像划分为固定的补丁,然后将这些补丁展平成一系列向量,并添加位置嵌入,之后这些向量将被送入 Transformer 编码器进行处理。

2. 隧道病害检测领域常用模型

在隧道病害检测领域,尤其是针对细小裂缝的检测,需要模型具备良好的细节捕捉能力和多尺度感知能力。以下是一些常用的模型及其特点:

  1. UNet

    • 特点: UNet 因其在医学图像分割中的成功应用而知名,同样适用于隧道病害检测。通过跳层连接(skip connections),UNet 能够结合高层语义信息与底层细节信息,这对于细小裂缝的检测非常重要。
    • 应用: 在隧道检测中,UNet 可以帮助识别裂缝等病害,特别是在数据尺度较小的情况下表现良好。
  2. DeepLabV3+

    • 特点: 使用空洞卷积(Atrous Convolution)来扩大感受野而不增加参数数量,并引入 ASPP 模块来捕获多尺度信息。DeepLabV3+还增加了额外的解码模块来恢复分割细节。
    • 应用: 对于隧道病害检测而言,DeepLabV3+的多尺度感知能力非常适合识别不同宽度和长度的裂缝。
  3. SENet (Squeeze-and-Excitation Networks)

    • 特点: 通过引入通道注意力机制来动态地调整通道权重,从而让模型更加关注于那些对于分类任务更重要的特征。
    • 应用: 在隧道病害检测中,SENet 可以通过加强裂缝区域的特征表达,来提高裂缝识别的连续性。
  4. HRNet (High-Resolution Net)

    • 特点: HRNet 在整个网络中都保持高分辨率的特征图,通过并行的多分支结构来融合不同尺度的信息,避免了在恢复分辨率过程中细节信息的丢失。
    • 应用: 这种特性对于隧道病害检测尤其有用,因为裂缝往往非常细小,需要保持尽可能高的分辨率来确保准确识别。
  5. SegFormer

    • 特点: SegFormer 结合了 Transformer 编码器(如 MiT)和简单的解码头来实现高效的多尺度特征提取。相比于传统的 CNN,Transformer 能够更好地捕捉全局上下文信息。
    • 应用: 在隧道病害检测中,SegFormer 可以通过其强大的全局感知能力来识别那些跨越较大区域的裂缝或其他病害。

Q: 在隧道病害检测中,为什么 UNet 的跳层连接很重要? A: 跳层连接允许 UNet 在解码过程中重新引入编码阶段丢失的细节信息。这对于细小裂缝的检测至关重要,因为裂缝通常很窄,容易在下采样的过程中丢失。

Q: DeepLabV3+的 ASPP 模块是如何工作的? A: ASPP 模块使用不同膨胀率的空洞卷积来捕捉不同尺度的信息,这样即使在不改变输出尺寸的情况下,也可以有效地扩大模型的感受野。

Q: SENet 的通道注意力机制如何帮助改进病害检测? A: 通道注意力机制允许 SENet 根据每个通道的重要性动态地调整权重,这意味着模型可以更加聚焦于那些最能代表病害特征的通道,从而提高检测精度。

Q: 在隧道病害检测中,HRNet 如何保证高分辨率特征图? A: HRNet 通过保持多个并行的高分辨率流,并在每一层之间交换信息,从而在整个网络中维持高分辨率特征图。这种方法有助于保留更多细节信息,这对于检测细小裂缝非常重要。

Q: SegFormer 如何在病害检测中发挥作用? A: SegFormer 利用 Transformer 的强大能力来捕捉全局依赖关系,并通过多尺度特征提取来增强对不同大小病害的检测性能。这对于识别隧道中各种类型的病害非常有效。

3. 如何处理小目标和大目标同时存在于一张图片中的情况?

在语义分割任务中,经常会遇到图像中小目标和大目标共存的情况。为了同时有效地检测和分割这些不同尺度的目标,可以采用以下几种策略和技术:

  1. 多尺度注意力金字塔 (Multi-Scale Attention Pyramid)

    • 解释: 多尺度注意力金字塔通过在不同尺度上应用注意力机制来捕获不同大小的目标。这通常涉及到构建一个多尺度特征金字塔,每个尺度上的特征图都会经过注意力机制处理,以突出不同尺度的目标。
    • 例子: 比如 DeepLab 系列中的 ASPP(Atrous Spatial Pyramid Pooling)模块就是一种典型的多尺度处理方式,它通过不同膨胀率的卷积来捕捉多尺度信息。
  2. 混合 CNN 和 Transformer (Hybrid CNN and Transformer Models)

    • 解释: 混合 CNN 和 Transformer 模型结合了传统卷积神经网络在局部特征提取方面的优势和 Transformer 在捕获长距离依赖关系方面的强大能力。这种组合可以在不同尺度上同时处理局部和全局信息。
    • 例子: SegFormer 就是一个实例,它使用了 Transformer 编码器(如 MiT)来提取多尺度特征,并结合了简单的解码头来进行最终的分割预测。

Q: 为什么多尺度注意力金字塔对于处理小目标和大目标是有效的? A: 多尺度注意力金字塔通过在多个尺度上进行特征提取,使得模型可以在不同级别的细节上关注目标,从而更好地捕捉到小目标的细节和大目标的整体形状。

Q: SegFormer 如何结合 CNN 和 Transformer 的优点? A: SegFormer 使用了基于 Transformer 的编码器来捕捉全局上下文信息,并通过多尺度特征提取来增强对不同大小目标的理解。同时,它的解码头设计简单高效,可以很好地将多尺度特征融合在一起,以实现高质量的分割结果。

Q: 在实际应用中,如何选择合适的多尺度处理方法? A: 选择多尺度处理方法时,应考虑应用场景的具体需求。如果场景中存在大量的小目标,则应选择那些能够较好地保留细节信息的方法;而对于包含大范围目标的场景,则可能需要更强的全局感知能力。

Q: 除了多尺度处理,还有哪些技术可以用来改善小目标和大目标的分割效果? A: 另外一些技术还包括使用金字塔结构(如 FPN)、增强数据(如数据扩增)、改进损失函数(如 Focal Loss)等方法,这些都可以辅助提升模型在不同尺度目标上的表现。

4. 你在实际项目中使用过哪些语义分割模型?遇到了什么挑战?怎么解决?

在实际项目中,我使用过多种语义分割模型来处理隧道病害检测的任务,包括但不限于 UNet、DeepLabV3+、HRNet 和 SegFormer。在具体的应用过程中,确实遇到了一些挑战,并采取了相应的解决方案。

  1. 裂缝和瓷砖剥落病害尺度不平衡

    • 挑战: 不同尺度的病害(如细小裂缝和大面积的瓷砖剥落)在图像中占比不同,这可能导致模型对某一类病害的检测能力较弱。
    • 解决方案:
      • 使用加权交叉熵损失函数,或 Focal Loss,来平衡不同类别之间的损失贡献,从而提高小目标的检测能力。
      • 结合 Transformer 和 CNN 的优势,利用 Transformer 捕捉全局信息,同时使用 CNN 来提取局部特征,以增强模型对不同尺度病害的感知能力。
  2. 病害图像背景复杂

    • 挑战: 背景复杂度高会干扰模型对病害关键特征的提取,导致误检或漏检。
    • 解决方案:
      • 使用原型特征提取方法,该方法能够学习到特定类别的原型特征,有助于在复杂背景下提取出病害的关键特征。
      • 利用 VQGAN 的预训练 CodeBook 来提取更为鲁棒的特征表示,增强模型的抗干扰能力。
  3. 标注不准确

    • 挑战: 数据标注过程中可能会出现误差,导致模型训练偏差或泛化能力下降。
    • 解决方案:
      • 采用软标签的学习方式,即在训练过程中使用带有不确定性的标签,而非硬性分配标签,这样可以减弱损失函数的强约束,使模型更具弹性。
      • 使用边缘优化方法,如 PointRend,来改进分割边界,或者采用边缘再分割技术,通过形态学操作(如膨胀、腐蚀)来选取合适的像素点,提高分割的准确性。

Q: Focal Loss 是如何解决类别不平衡问题的? A: Focal Loss 通过降低易分类样本的权重,从而更加关注难以分类的样本。这样可以减轻类别不平衡带来的影响,尤其是在小目标检测中表现得尤为明显。

Q: Transformer 和 CNN 的结合如何提高模型性能? A: Transformer 擅长捕捉全局依赖关系,而 CNN 则在局部特征提取方面表现出色。将两者结合起来可以互补各自的优势,使得模型既能捕捉到局部细节又能理解整体上下文。

Q: 原型特征提取方法是如何工作的? A: ProtoPNet 通过学习一组原型特征,并在测试时计算输入图像与这些原型特征之间的相似度,从而决定分类结果。原型特征为一类像素特征的均值,且随着训练不断变化。这种方法可以增强模型对特定类别的理解,并提高其在复杂背景下的鲁棒性。

Q: 使用 VQGAN 的预训练 CodeBook 有什么好处? A: 使用 VQGAN 的预训练 CodeBook 可以帮助模型学习到更加紧凑和有意义的离散特征表示,这对于处理复杂背景下的病害检测任务非常有帮助,可以减少背景噪声的影响。

Q: PointRend 是如何优化分割边界的? A: PointRend 通过在分割边界处选择不确定性较高的像素点重预测,来细化分割结果。这种方法可以在保持较高效率的同时,显著提高分割边界的准确性。

Q: 6. 除了 Self-Attention,还有哪些机制可以增强模型的表达能力? A: (层归一化(Layer Normalization)可以帮助模型更好地学习长距离依赖;残差连接(Residual Connections)有助于梯度流动;使用 Transformer 中的多头注意力机制)

损失函数

1. 介绍一下常用的损失函数

  1. 交叉熵损失(Cross Entropy Loss)

    • 解释: 交叉熵损失是最常见的分类损失函数之一,它衡量的是模型预测的概率分布与真实标签的概率分布之间的差异。

    • 代码示例:

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      17
      18
      19
      20
      21
      22
      23
      import torch
      import torch.nn as nn
      import torch.nn.functional as F

      class CrossEntropyLoss(nn.Module):
      def __init__(self, weight=None, reduction='mean'):
      super(CrossEntropyLoss, self).__init__()
      self.weight = weight
      self.reduction = reduction

      def forward(self, pred, label):
      # pred (B, C, H, W)
      # label (B, H, W)
      if len(label.shape) < len(pred.shape): # 如果标签不是one-hot形式
      label = F.one_hot(label, num_classes=pred.shape[1])
      pred = F.softmax(pred, dim=1)
      loss = -label * torch.log(pred)
      if self.weight is not None:
      loss = loss * self.weight.view(1, - 1, 1, 1)
      if self.reduction == 'mean':
      return loss.mean()
      elif self.reduction == 'sum':
      return loss.sum()
  2. Focal Loss

    • 解释: Focal Loss 旨在解决类别不平衡的问题,通过在交叉熵的基础上增加一个调节因子来降低容易分类样本的权重,增加难分类样本的权重。

    • 代码示例:

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      17
      18
      19
      20
      21
      class FocalLoss(nn.Module):
      def __init__(self, weight=None, reduction='mean', gamma=2):
      super(FocalLoss, self).__init__()
      self.weight = weight
      self.reduction = reduction
      self.gamma = gamma

      def forward(self, pred, label):
      # pred (B, C, H, W)
      # label (B, H, W)
      if len(label.shape) < len(pred.shape):
      label = F.one_hot(label, num_classes=pred.shape[1])
      pred = F.softmax(pred, dim=1)
      pt = torch.where(label > 0, pred, 1 - pred)
      loss = -torch.pow(1 - pt, self.gamma) * label * torch.log(pt)
      if self.weight is not None:
      loss = loss * self.weight.view(1, -1, 1, 1)
      if self.reduction == 'mean':
      return loss.mean()
      elif self.reduction == 'sum':
      return loss.sum()
  3. Dice 损失

    • 解释: Dice 损失通常用于分割任务中,特别是当需要关注分割边界时。它定义为两个集合交集的两倍除以它们的并集。

    • 公式: ( DICE = 1 - ),其中( X )是预测结果,( Y )是真实标签。

    • 代码示例:

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      class DiceLoss(nn.Module):
      def __init__(self):
      super(DiceLoss, self).__init__()

      def forward(self, pred, label):
      smooth = 1.
      pred = F.softmax(pred, dim=1)
      if len(label.shape) < len(pred.shape):
      label = F.one_hot(label, num_classes=pred.shape[1])
      intersection = (pred * label).sum(dim=(2, 3))
      dice_score = (2. * intersection + smooth) / (pred.sum(dim=(2, 3)) + label.sum(dim=(2, 3)) + smooth)
      return 1 - dice_score.mean()

Q: 为什么交叉熵函数在不平衡数据表现不佳? A: 交叉熵函数在不平衡数据集中表现不佳的原因在于,它会过度强调多数类别的样本,而忽略少数类别的样本。在不平衡数据集中,少数类别的样本往往包含更有价值的信息,但交叉熵损失函数并没有专门对待这些样本,导致模型倾向于偏向多数类别。

Q: Focal Loss 是如何解决类别不平衡的问题的? A: Focal Loss 通过引入一个调节因子( (1 - p_t)^{} ),其中( p_t )是模型对正确类别的预测概率,( )是调节因子的指数。这个调节因子降低了容易分类样本的贡献,同时增加了难分类样本的贡献,从而使得模型更加关注那些难以分类的样本。

Q: Class Weight 是如何帮助平衡数据的? A: Class Weight 是通过为不同类别赋予不同的权重来实现的,这样可以调整损失函数中各类别对总损失的贡献比例。在不平衡数据集中,可以为少数类别赋予更高的权重,从而增加它们在训练过程中的重要性。

Q: 如何平衡正负样本的比例来改善模型性能? A: 平衡正负样本比例可以通过多种方法实现,例如过采样少数类别、欠采样多数类别、使用合成样本(如 SMOTE)、调整 Class Weight 等。这些方法可以单独使用或组合使用,以达到更好的模型训练效果。此外,还可以在训练过程中动态调整样本权重,以进一步优化模型性能。

数据集构建

1. 数据处理的过程

  • 数据收集: 收集来自不同来源的原始数据。
  • 预处理: 包括数据格式转换、缩放、裁剪等操作。
  • 清洗: 移除或修正错误、重复或无关的数据。
  • 标注: 对数据进行标记,以便机器学习模型可以学习到正确的模式。
  • 划分: 将数据分成训练集、验证集和测试集,用于模型训练、调参和评估。

2. 数据收集

  • 采集车采集隧道衬砌图像: 使用专门的采集设备在隧道内拍摄衬砌图像,确保图像质量和涵盖不同类型的衬砌材料。

3. 数据标注

  • LabelMe: 使用 LabelMe 这样的工具进行手动标注,确保标注的准确性和一致性。

4. 数据预处理

  • 局部匀光算法: 对图像进行光照均匀化处理,消除光照不均带来的影响。
  • 数据分块: 将大图像分割成若干个小块,便于处理和标注。

5. 数据清洗

  • 去除重复数据: 通过哈希或特征匹配等方式识别并删除重复项。
  • 修复损坏文件: 检查并修复损坏的图像文件。
  • 清理噪声: 去除不需要的对象或背景干扰。

6. 数据划分

  • 随机划分: 使用随机种子将数据集分成训练、验证和测试集。
  • 按类别划分: 确保每个子集中都有各个类别的代表性样本。

7. 如何处理数据集中存在的标注错误?

  • 复查标注: 定期复查已有的标注,确保标注的一致性和准确性。
  • 使用一致性检查: 应用一致性检查工具来发现和纠正标注错误。
  • 引入专家审查: 让领域专家复审标注结果,尤其是对于复杂的案例。

8. 在数据集构建过程中,如何保证数据的多样性和代表性?

  • 涵盖不同场景: 确保数据覆盖隧道的不同部分,如墙壁、天花板、地面等。
  • 不同条件: 包括白天、夜晚、晴天、雨天等多种天气和光照条件。
  • 不同材质: 包括瓷砖、混凝土、金属等多种衬砌材料。
  • 不同病害类型: 包括裂缝、剥落、渗水等多种病害形式。

9. 有哪些工具或技术可以用来自动化数据标注过程?

  • Paddle: 使用 Paddle 框架提供的工具和服务进行自动化的数据标注。
  • LabelStudio: LabelStudio 是一个开源的标注工具,支持多种数据类型和标注任务,可以用于简化数据标注流程。

Q: 局部匀光算法是如何工作的? A: 局部匀光算法通常通过调整图像的局部对比度或亮度来均匀化光照条件。计算局部块的平均灰度,上采样和高斯模糊得到亮度图,计算原图与亮度图的差异还原亮度分布。还可以使用直方图均衡化、Retinex 算法或自适应直方图均衡化(CLAHE)等方法来改善光照不均的问题。

Q: 数据分块的好处是什么? A: 数据分块可以使处理和标注工作更加高效。通过将图像分割成小块,可以更容易地进行并行处理,同时也有助于标注人员专注于图像的特定区域。

Q: 数据清洗中的“清理噪声”具体指的是什么? A:

Q: 如何确保数据集划分的合理性? A: 确保数据集划分合理的方法之一是使用分层抽样,这样可以确保每个子集中都有各个类别的代表性样本。此外,可以使用交叉验证来评估模型在不同子集上的表现。

Q: 自动化数据标注技术的局限性是什么? A: 自动化数据标注虽然提高了效率,但也可能存在误标的情况,尤其是在数据复杂或变化多端的情况下。因此,通常还需要人工复查和修正标注结果。

训练方法研究

1. MMCV

  • 解释: MMCV 是一个基于 PyTorch 的开放源码计算机视觉工具箱,它提供了丰富的模型实现、数据处理和训练框架。
  • 用途: MMCV 可以帮助快速搭建和训练模型,同时也提供了很多实用功能,如数据增强、模型融合等。

2. 训练框架

  • Config: 配置文件用于定义整个训练过程的参数,包括数据路径、模型结构、损失函数、优化器等。
  • Data: 数据加载器负责读取、预处理和批处理数据。
  • Model: 模型定义,包括网络结构和前向传播逻辑。
  • Loss: 损失函数用于量化模型预测与真实标签之间的差距。
  • Trainer: 训练循环逻辑,包括前向传播、反向传播、优化更新等。

3. PytorchLightning

  • 解释: PytorchLightning 是一个用于简化 PyTorch 模型开发的库,提供了一套简洁的 API 来管理训练流程。
  • 优点: 减少了样板代码,方便配置和调试,支持多种训练策略如 GPU 分布式训练、混合精度训练等。

4. 学习率的选择

  • 解释: 学习率决定了模型参数更新的速度。过高会导致训练不稳定甚至发散,过低则会使训练速度过慢。
  • 策略: 可以通过学习率查找(Learning Rate Finder)来找到合适的初始学习率。

5. 优化器的选择

  • 解释: 优化器决定了梯度下降的方式,常用的有 SGD、Adam、RMSprop 等。
  • 选择: 根据任务特性和模型结构选择合适的优化器,例如 Adam 适合稀疏数据,SGD 适合大规模数据集。

6. 显存问题

  • 解释: 训练深度学习模型时,显存不足是一个常见问题。
  • 解决: 可以通过梯度累积、模型剪枝、分批加载数据等方式缓解显存压力。

7. 如何有效地使用迁移学习来加速模型训练?

  • 使用预训练模型作为初始权重: 从预训练模型加载权重,可以加速收敛并提高性能。
  • 冻结基础层,仅训练顶层: 在训练初期可以冻结预训练层,只训练新添加的层。
  • 适应性调整预训练模型的输出层以匹配新的任务: 修改输出层以适应新的任务需求。

8. 如何设置学习率衰减策略来避免过拟合?

  • 使用学习率调度器如 StepLR、Cosine Annealing 等: 通过周期性地降低学习率来促进收敛。
  • 观察验证集上的性能变化来动态调整学习率: 当验证集性能不再提升时,可以适当降低学习率。
  • 使用早停法(Early Stopping): 在验证集性能不再改善时提前终止训练。

9. 在训练过程中,如何监控和诊断模型的训练状态?

  • 使用 TensorBoard 或其他可视化工具来跟踪损失和指标: 监控训练过程中的损失曲线和指标变化。
  • 定期保存检查点并进行评估: 保存中间训练结果,便于后续评估或恢复训练。
  • 记录训练过程中的关键参数和配置: 保持训练配置的一致性和可重复性。

10. DDP (Distributed Data Parallel)

  • 解释: DDP 是 PyTorch 中的一个分布式训练工具,允许多个 GPU 并行训练同一个模型。
  • 使用: 可以通过设置 torch.nn.parallel.DistributedDataParallel 来启用 DDP 训练。

11. 混合精度

  • 解释: 混合精度训练是指在模型训练过程中同时使用单精度(32 位)和半精度(16 位)浮点运算。
  • 优势: 可以减少内存占用,加快训练速度,同时保持较高的精度。

Q: MMDetection 有哪些主要组件? A: MMDetection 主要包括数据读取、模型定义、训练流程管理、评估工具等多个组件,支持多种模型和任务的快速开发。

Q: 如何选择合适的优化器? A: 选择优化器时需要考虑任务的特性和数据集的特点。例如,对于稀疏数据,Adam 通常表现较好;而对于大规模数据集,SGD 由于其更快的收敛速度可能是更好的选择。

Q: 如何解决显存不足的问题? A: 可以通过使用梯度累积、模型剪枝、数据分批加载等方法来缓解显存不足的问题。此外,还可以考虑使用更大的显卡或者分布式训练方案。

Q: 学习率查找是如何工作的? A: 学习率查找通过逐渐增加学习率并观察损失的变化趋势来确定一个好的初始学习率。通常会在训练初期执行一次,以找到损失开始显著下降的学习率值。

Q: 如何使用早停法来避免过拟合? A: 在训练过程中,当验证集的性能不再提高时,可以停止训练。这通常通过监测验证集上的损失或准确率来实现,当这些指标在一个预定的周期内没有改善时,就触发早停。

低光增强及图像复原模型研究

1. RefinxNet

  • 解释: RefinxNet 基于 Refinx 原理分离亮度和细节。
  • 特点: RefinxNet 通过多级特征融合,增强了对细节的捕捉能力,并且使用残差学习来减少训练难度。

2. Zero-DCE

  • 解释: Zero-DCE 是一种无参考的低光图像增强方法,它不需要任何参考图像即可完成增强任务。
  • 特点: Zero-DCE 通过学习图像的亮度和色彩分布来调整图像,使得在没有任何参考图像的情况下也能获得较好的增强效果。

3. DDPM

  • 解释: DDPM(Diffusion Denoising Probabilistic Models)是一种基于扩散过程的图像生成模型,也可以应用于图像复原任务。
  • 特点: DDPM 通过逐步去除噪声来恢复图像,适用于多种图像复原任务。

4. ControlNet

  • 解释: ControlNet 是一种可以控制生成过程的模型,可以在图像复原任务中引入额外的控制信号。
  • 特点: ControlNet 可以根据额外的输入(如边缘图、分割图等)来引导图像复原过程,提高复原的准确性和可控性。

5. LocalLightEnhance

  • 解释: LocalLightEnhance 是一种局部光照增强方法,通过局部调整图像的光照来提高图像质量。
  • 特点: LocalLightEnhance 更加注重局部细节的恢复,适用于需要精细调整光照的场景。

6. Position Embedding

  • 解释: 位置嵌入(Position Embedding)是在 Transformer 模型中引入的一种机制,用于捕捉序列中元素的位置信息。
  • 公式: ( pos{(2i)} = (x / i{}) ), ( pos{(2i+1)} = (x / i{}) )
  • 类型: 包括相对位置编码和空间位置编码,前者用于捕捉序列元素之间的相对位置,后者用于标记序列中元素的空间位置。

7. HunyuanDiT

  • 解释: HunyuanDiT 是一种用于图像复原的扩散模型,结合了多尺度特征提取和注意力机制。
  • 特点: HunyuanDiT 通过多尺度特征提取来捕捉不同层次的细节,并通过注意力机制来加强重要特征的表达。

8. 如何评估低光图像增强算法的效果?

  • 定量指标: 使用 LOE(Low Light Enhancement)、PSNR(峰值信噪比)、SSIM(结构相似性指数)等指标来评估图像质量。
  • 主观反馈: 通过用户研究或专家评审来获取关于图像视觉效果的主观反馈。
  • 视觉效果: 比较增强前后图像的视觉效果,评估算法在实际应用中的表现。

8. 对于极端低光条件下的图像,有哪些有效的增强方法?

  • 增强曝光度: 通过增加曝光度来提高图像的整体亮度。
  • 局部调整: 使用局部光照增强方法来恢复图像的细节。
  • 多帧融合: 通过融合多张连续拍摄的低光图像来减少噪声并提高图像质量。
  • 预处理: 在增强前进行预处理,如去除噪声或增强对比度。

9. 如何利用先验知识来改进图像复原模型?

  • 物理模型: 引入物理模型来模拟成像过程,帮助模型更好地理解图像退化的原因。
  • 场景特定知识: 根据特定场景的特点,如光照方向、纹理特征等,对模型进行定制化调整。
  • 上下文信息: 利用上下文信息(如图像中的语义信息)来指导图像复原过程。
  • 多模态信息: 结合其他模态的数据(如深度信息、语义分割图等)来增强图像复原的效果。

Q: RefinxNet 中的多尺度特征融合是如何实现的? A:

Q: Zero-DCE 的优势是什么? A: Zero-DCE 的最大优势在于它不需要参考图像即可完成增强任务,这使得它在实际应用中更加便捷。

Q: DDPM 在图像复原中的作用是什么? A: DDPM 通过逐步去除图像中的噪声来恢复图像的原始信息,适用于多种复原任务。

Q: ControlNet 在图像复原中的应用有哪些? A: ControlNet 可以通过引入额外的控制信号来引导图像复原过程,从而实现更精确的复原效果。

Q: 如何选择合适的定量指标来评估图像增强的效果? A: 选择指标时需要考虑具体的评估目标,如 LOE 侧重于低光环境下的增强效果,而 PSNR 和 SSIM 则更多关注图像的整体质量。

Q: 在极端低光条件下,多帧融合为什么有效? A: 多帧融合可以利用多张图像中的信息来补偿单张图像中的信息不足,从而提高图像质量。

Q: 如何利用场景特定知识来改进图像复原模型? A: 可以根据场景的特点,如光照条件、纹理特征等,对模型进行定制化调整,使其更适合特定场景的应用。

图像处理算法

  1. 低通滤波

    • 解释: 低通滤波器用于平滑图像,去除高频噪声,保留低频成分。
    • 应用: 低通滤波常用于图像去噪、模糊处理等场景。
    • 例子: 常见的低通滤波器有均值滤波器、高斯滤波器等。
  2. 边缘提取算法

    • 解释: 边缘提取算法用于检测图像中的边缘,即像素强度的急剧变化。
    • 应用: 边缘检测广泛应用于图像分割、特征识别等领域。
    • 例子: 常见的边缘提取算子有 Sobel 算子、Canny 边缘检测、Prewitt 算子等。
  3. 在不同的应用场景中,如何选择适合的滤波器?

    • 根据需求选择滤波器类型: 例如,去噪可以选择高斯滤波,边缘检测可以选择 Sobel 算子。
    • 考虑滤波器的频率响应特性: 不同滤波器对不同频率成分的处理效果不同,需根据实际需求选择合适的滤波器。
  4. 如何结合多种边缘提取算法来获得更好的效果?

    • 组合使用: 可以将多种边缘提取算法的结果进行组合,例如先用 Canny 边缘检测提取粗略边缘,然后再用 Sobel 算子细化边缘。
    • 多尺度处理: 在不同尺度上应用不同的边缘检测算法,然后综合结果,以提高边缘检测的鲁棒性。
    • 融合算法: 利用融合算法(如投票机制)来综合多种边缘检测算法的结果,以获得更准确的边缘。
  5. 除了传统的边缘检测算法,还有哪些现代方法?

    • 深度学习方法: 使用卷积神经网络(CNN)进行边缘检测,例如基于 U-Net、SegNet 等网络架构的边缘检测模型。
    • 超像素分割: 利用超像素分割技术,将图像分割成多个超像素区域,然后在超像素级别进行边缘检测。
    • 图割方法: 利用图论中的图割方法来检测图像中的边缘。
    • 主动轮廓模型(Snake 模型): 通过能量最小化的方法来寻找图像中的边缘。

Q: 高斯滤波器和平均滤波器有什么区别? A: 高斯滤波器通过高斯函数加权平均邻域内的像素值,可以有效地保留图像的主要特征,同时去除噪声。而平均滤波器则是简单地取邻域内像素的平均值,可能会导致图像模糊。

Q: Sobel 算子的工作原理是什么? A: Sobel 算子通过两个 3x3 的卷积核分别对图像进行水平和垂直方向的卷积,从而计算图像在两个方向上的梯度,进而检测出边缘。

Q: 在图像处理中,如何选择合适的滤波器大小? A: 滤波器的大小取决于需要处理的特征的尺度。较大的滤波器可以处理更大范围的特征,但可能会丢失细节;较小的滤波器则更适合处理局部特征。

Q: 如何评估边缘检测算法的效果? A: 可以通过定量指标(如边缘检测的准确率、召回率等)和定性评价(如视觉效果)来评估边缘检测算法的效果。此外,还可以使用人工标注的边缘作为基准来比较算法的性能。

Q: 深度学习在边缘检测中的优势是什么? A: 深度学习方法可以自动学习特征表示,具有很强的表达能力和适应性,可以处理复杂的边缘检测任务,并且在大数据集上有很好的表现。

分割边缘优化

  1. PointRend
  2. Multimul DataSyn
  3. SegRefiner
  4. 如何评价分割边缘的质量?
  5. 在分割任务中,如何平衡速度和精度?
  6. 有没有尝试过将其他领域的技术应用于分割边缘优化?

Transformer 模型

  1. Transformer 模型是如何处理长依赖关系的?
  2. 如何将 Transformer 应用于非自然语言处理的任务?
  3. Transformer 模型的局限性是什么? (计算成本高,尤其是在长序列上;训练数据需求量大;难以捕捉局部特征)

Diffusion 模型

1. Diffusion 模型的训练过程

  • 正向扩散过程: 在这一过程中,原始数据被逐渐添加高斯噪声,直到变成纯噪声为止。这一过程可以看作是一个数据退化的过程,目的是构造一个从清晰数据到噪声的连续分布演变。
  • 逆向扩散过程: 该过程尝试从噪声中逐步去除噪声,逐步重建原始数据。此过程涉及训练一个模型,使其能够预测在某一步骤中应该去除多少噪声。

2. Diffusion 模型与 GAN 模型的区别

  • 显式地学习噪声分布: Diffusion 模型通过显式地学习噪声分布来生成数据,而 GAN 则是通过生成器和判别器之间的对抗训练来间接学习数据分布。

3. 如何在 Diffusion 模型中加入条件信息?

  • 使用条件向量作为输入的一部分: 条件信息可以直接作为模型输入的一部分,帮助指导生成过程。
  • 在生成过程中加入外部信息: 例如,在文本到图像生成中,可以将文本描述嵌入到模型中,如 StableDiffusion 通过交叉注意力机制融合特征。
  • ControlNet: 在某些情况下,可以通过增加一个可训练的分支并将条件信息通过跳层连接引入,类似于 ControlNet 的做法。

4. 在图像生成任务中,Diffusion 模型相比传统方法有什么优势?

  • 学习分布时任务目标更简单: Diffusion 模型通过逐步添加和去除噪声来学习数据分布,这比直接学习复杂的高维数据分布要简单得多。
  • 速度较慢: 尽管任务目标简单,但由于需要多次迭代去除噪声,因此生成过程相对缓慢。

5. 如何评估 Diffusion 模型的生成质量?

  • 结果容易模糊: Diffusion 模型由于其生成过程的本质,可能会导致生成的图像模糊不清。评估时可以使用诸如 Fréchet Inception Distance (FID) 或 Inception Score (IS) 等指标来量化生成图像的质量。
  • 定性评估: 除了量化指标外,还可以通过人工视觉评估来检查生成图像的真实感和多样性。

6. Diffusion 推理加速

  • 并行化: 利用 GPU 的并行计算能力来加速每一步的去噪过程。
  • 采样步数减少: DDIM 通过减少去噪步骤的数量来加速推理,但这可能会影响生成图像的质量。
  • 模型剪枝: 通过对模型进行剪枝,减少不必要的计算资源消耗。
  • 量化: 通过量化技术减少模型大小和计算复杂度,从而加快推理速度。

Q: Diffusion 模型中的正向扩散过程如何实现? A: 正向扩散过程通常通过一系列高斯噪声的添加来实现,每次添加一定强度的噪声,直到原始数据完全被噪声掩盖。这一过程可以视为数据分布的退化。

Q: Diffusion 模型中的逆向扩散过程是如何去噪的? A: 逆向扩散过程通过训练一个去噪模型来逐步去除噪声,每次迭代都试图预测并移除一定量的噪声,直至恢复出原始数据。

Q: 控制 Diffusion 模型生成结果的方法有哪些? A: 可以通过条件输入(如类别标签、文本描述等)来控制生成结果,或者通过调整模型参数(如去噪步数、噪声强度等)来微调生成效果。

Q: Diffusion 模型在生成图像时为什么会模糊? A: 由于 Diffusion 模型需要多次迭代去除噪声,这个过程中累积的小误差可能会导致生成的图像变得模糊不清。

Q: 如何解决 Diffusion 模型生成结果模糊的问题? A: 可以尝试改进去噪算法,比如引入注意力机制来增强模型的局部感知能力,或者采用后处理技术(如锐化滤波)来增强生成图像的清晰度。

多模态模型

  1. SAM
  2. CLIP
  3. BLIP
  4. HunyuanDiT

大语言模型

  1. RAG 工程
  2. Prompt 优化

图像处理

1.对深度学习相关神经网络理解深入,如 DNN、CNN、RNN、GAN 等; 2.有深厚的理论研究背景和数据基础,熟悉 EM、MCMC、LR、LDA、PCA、时间序列等数学方法; 4.熟悉一种以上的深度学习的开源框架,如 Caffe、TensorFlow、ARMAILibrary、SNPE、OpenGLES 等。

AMD GPU MI210 深度学习疑难杂症

ROCm 官方文档

ROCm

Pytorch

PyTorch for ROCm 官方文档

方法一:使用 docker 镜像 rocm/pytorch

方法二:Pytorch 官方轮子

APEX

  • Pytorch 扩展,用于混合精度与分布式训练的工具
  • Github

ModuleNotFoundError: fused_layer_norm_cuda

通过源码安装 APEX 解决,注意 Pytorch 版本对应的源码分支

  1. GitHub 拉取相应分支源码
  2. cd apex
  3. 输入命令安装 apex,耗费时间可能较长
1
2
3
4
5
# if pip >= 23.1 (ref: https://pip.pypa.io/en/stable/news/#v23-1) which supports multiple `--config-settings` with the same key...
pip install -v --no-build-isolation --config-settings "--build-option=--cpp_ext" --config-settings "--build-option=--cuda_ext" ./

# otherwise
python setup.py install --cpp_ext --cuda_ext

区间题目集合

leetcode 打气球

右端点排序,合并区间

美团种树

随着种树数量的增加,树总量单调递增,可以通过二分法查询种树量

美团流星

左端点和右端点分开排序,计算最大经过区间数量

Hunyuan-DiT

  • Paper: Hunyuan-DiT : A Powerful Multi-Resolution Diffusion Transformer with Fine-Grained Chinese Understanding

  • Authors: Zhimin Li, Jianwei Zhang, Qin Lin, Jiangfeng Xiong, Yanxin Long, Xinchi Deng, Yingfang Zhang, Xingchao Liu, Minbin Huang, Zedong Xiao, Dayou Chen, Jiajun He, Jiahao Li, Wenyue Li, Chen Zhang, Rongwei Quan, Jianxiang Lu, Jiabin Huang, Xiaoyan Yuan, Xiaoxiao Zheng, Yixuan Li, Jihong Zhang, Chao Zhang, Meng Chen, Jie Liu, Zheng Fang, Weiyan Wang, Jinbao Xue, Yangyu Tao, Jianchen Zhu, Kai Liu, Sihuan Lin, Yifu Sun, Yun Li, Dongdong Wang, Mingtao Chen, Zhichao Hu, Xiao Xiao, Yan Chen, Yuhong Liu, Wei Liu, Di Wang, Yong Yang, Jie Jiang, Qinglin Lu

  • Code & Pretrained Model: GitHub

背景

  • 现有一些基于 Diffusion 的文生图模型,如 DALL-E、SD 和 Pixart 缺乏对中文提示词的理解,而 AltDiffusion、PAI-Diffusion 和 Taiyi 这一类具有中文理解能力的模型则仍有进步空间

基于 DiT 的模块改进

Hunyuan-DiT

图像编码器

使用预训练 VAE 提取图像编码用于学习数据分布,SDXL 中的 VAE 相比于 SD1.5 中的 VAE 有较大的提升

文本编码器

使用预训练中英双语 CLIP 模型以及多语种 T5 模型提取文本编码

混元 DiT

  • 按照的大小分块
  • 为了提升模型在细粒度文本条件表现,在特征提取模块使用交叉注意力层融合文本特征
  • Transformer 块包含编码块和解码块,块中包含了自注意力-交叉注意力-FFN
  • 在解码块增加了与编码块之间的跳层链接
  • 训练时使用 v-prediction 的方式具有更好的表现

v-predition 相关资料 在使用 v-prediction 方法时,模型不直接预测噪声 ε,而是预测了一个加权后的量 v,这个量结合了噪声 ε 和原始数据 x 的信息,能在采样步骤较少的情况下提供有效的信号来指导采样过程

位置编码和多分辨率图像生成

两种位置编码可视化
  • 使用二维 RoPE 对绝对位置和相对位置进行编码
  • 为了实现多分辨率图像生成,尝试了两种类型的编码
    • Extended Positional Encoding,随着宽高的不同,编码结果也会有巨大的差异
    • Centralized Interpolative Positional Encoding,定义边界为编码结果变化的范围,且以图像中心为编码 0 点

提升训练稳定性

  • 使用 QK-Norm,在计算 Q、K 和 V 之前增加归一化层
  • 在跳层模块后增加归一化层,从而避免梯度爆炸
  • 使用 FP32 进行训练避免溢出

数据流

数据收集与筛选

图像重标注

多轮对话增强提示

DEADiff

  • Paper: DEADiff: An Efficient Stylization Diffusion Model with Disentangled Representations

  • Authors: Tianhao Qi, Shancheng Fang, Yanze Wu, Hongtao Xie, Jiawei Liu, Lang Chen, Qian He, Yongdong Zhang

  • Code & Dataset: GitHub

研究背景

  • 基于扩散模型的文本-图像生成模型(T2I)的发展,一些工作尝试引入参考图像作为生成模型的状态,风格图像就是其中一种
  • 利用T2I的已有工作
    • 基于本文转换的方法,将风格图像编码为文本嵌入空间的编码,这种图像到文本的模态转换容易导致信息的丢失
    • 针对风格微调参数的方法容易导致过拟合,且在现实生产中不具有实用性
    • 通过图像编码器提取风格图像特征
      • T2IAdapter-Style 和 IP-Adapter 使用 Transformer 作为图像编码器,以 CLIP 图像嵌入作为输入,并通过 U-Net 交叉注意层利用提取的图像特征
      • BLIP-Diffusion 通过 Q-Former 将图像嵌入转化为文本嵌入空间,作为扩散模型文本编码器的输入

研究方法

参考资料

Querying Transformer(Q-Former)

  • 由 Image Transformer 和 Text Transformer 组成,共享 Self-Attention 层参数
  • Image Transformer 提取与本文内容最相近的视觉特征
    • 输入:图像特征和可学习 Queries
    • 由于共享 Self-Attention 层参数,Queries 可同时与图像特征和文本特征进行交互
  • Text Transformer 作为输入文本的编码器和解码器

提取风格特征和内容特征

解耦风格特征与内容特征提取

DEADiff
  • STRE(Style Representation Extraction)
    • 使用风格相同的图像作为扩散模型的风格图像和输出目标
    • CLIP 提取的风格图像特征作为Q-Former输入的图像特征,文本“Style”提取特征作为Q-Former的文本特征,内部做交叉注意力,输出与文本相关的图像特征作为风格特征
  • SERE(Content Representation Extraction)
    • 使用主体相同但风格不同的图像作为扩散模型的风格图像和输出目标
    • CLIP 提取的风格图像特征作为Q-Former输入的图像特征,文本“Content”提取特征作为Q-Former的文本特征,内部做交叉注意力,输出与文本相关的图像特征作为内容特征

Disentangled Conditioning Mechanism(DCM)分离条件机制

在使用Diffusion模型去噪的过程中,提取的风格特征和语义特征将作为交叉注意力层的状态输入,从而引导模型更有效地分离风格特征和语义特征

模型使用Stable Diffusion v1.5作为文本-图像生成模型,将16个交叉注意力层编号为0-15,其中,4-8层为Coarse层,其余为Fine层

Disentangled Conditioning Mechanism
  • 输入
    • 风格信息将作为高分辨率Fine层的状态输入,使得提取的风格特征更注重笔画、纹理和颜色等细节信息
    • 语义信息将作为低分辨率Coarse层的状态输入
  • 网络结构 Text-image Crossattention Layer
    • 1)计算图像特征的Key和Value
    • 2)固定参数计算文本特征的Key和Value
    • 3)计算Query
    • 4)分别拼接图像和文本的Key以及图像和文本的Value
    • 5)计算交叉注意力

构建成对数据

准备主体词列表和风格词列表,组合得到相同主体或相同风格的提示词对,利用Text-to-images模型生成图像

  1. 构建文本提示词
    • 1)主体词:人物、动物、物体和场景四种类别,12000
    • 2)风格词:艺术风格、艺术家风格、笔触等,650
    • 3)1个主体词对应约14个风格词构成提示词组合,160000
  2. Midjourney生成图像 1个提示词生成4张分辨率为的图像,上采样到后,构建文本-图像对,1060000
  3. 成对图像选择
    • 1)风格特征学习:随机选择相同提示词生成的图像构成图像对
    • 2)内容特征学习:随机选择主体词相同但风格不同的提示词对应的图像对

p