主要内容

基于R-CNN深度学习的列车目标检测器

这个例子展示了如何使用深度学习和R-CNN(带卷积神经网络的区域)来训练目标检测器。

概述

此示例显示如何训练R-CNN对象检测器以检测停止标志。R-CNN是一种物体检测框架,它使用卷积神经网络(CNN)来对图像内的图像区域进行分类[1]。R-CNN检测器代替使用滑动窗口对每个区域进行分类,而是仅处理可能包含对象的那些区域。这大大降低了运行CNN时产生的计算成本。

为了说明如何培训R-CNN停车标志检测器,本例遵循了深度学习应用程序中常用的转移学习工作流。在迁移学习中,在大量图像集合(如ImageNet[2])上训练的网络被用作解决新分类或检测任务的起点。使用这种方法的优点是,预训练网络已经学习了一组丰富的图像特征,这些特征适用于广泛的图像。通过微调网络,这种学习可以转移到新任务中。通过对权重进行微调,可以微调网络,从而稍微调整为原始任务学习的特征表示,以支持新任务。金宝app

迁移学习的优点是减少了训练所需的图像数量和训练时间。为了说明这些优点,本示例使用迁移学习工作流训练一个停止标志检测器。首先,CNN使用CIFAR-10数据集进行预训练,该数据集有50,000张训练图像。然后,这个预先训练过的CNN只使用41张训练图像就可以进行停止标志检测。如果没有预先训练CNN,训练停止标志检测器将需要更多的图像。

注意:这个例子需要计算机视觉工具箱™,图像处理工具箱™,深度学习工具箱™,以及统计和机器学习工具箱™。

使用支持CUDA的NVIDIA™ 强烈建议运行此示例时使用GPU。使用GPU需要并行计算工具箱™. 有关支持的计算功能的信息,请参阅金宝appGPU通金宝app过发布支持(并行计算工具箱)

下载CIFAR-10图像数据

下载CIFAR-10数据集[3]。该数据集包含50,000张训练图像,将用于训练CNN。

将CiFar-10数据下载到临时目录

cifar10Data=tempdir;url='https://www.cs.toronto.edu/~kriz/cifar-10-matlab.tar.gz'; 下载(url,cifar10Data);

加载CIFAR-10培训和测试数据。

[培训剪辑,培训标签,testimages,testlabels] = Helpercifar10data.load(cifar10data);

每个图像是一个32x32 RGB图像,有50000个训练样本。

尺寸(培训图像)
ans=1×432 32 3 50000

CIFAR-10有10个图像类别。列出图像类别:

numImageCategories = 10;类别(trainingLabels)
ans=10×1个细胞{‘飞机’}{‘汽车’}{‘鸟’}{‘猫’}{‘鹿’}{‘狗’}{‘青蛙’}{‘马’}{‘船’}{“卡车”}

您可以使用以下代码显示一些训练图像。

图形缩略图=训练图像(:,:,:,1:100);蒙太奇(缩略图)

创建卷积神经网络(CNN)

CNN由一系列层组成,其中每个层定义特定计算。深度学习工具箱™提供功能,可轻松设计CNN层逐层。在此示例中,以下图层用于创建CNN:

此处定义的网络类似于[4]中描述的网络,以imageInputLayer.输入层定义了CNN可以处理的数据的类型和大小。在本例中,CNN用于处理CIFAR-10图像,图像为32x32 RGB:

%为32x32x3 CIFAR-10图像创建图像输入层。[height,width,NumChannel,~]=大小(训练图像);imageSize=[height-width NumChannel];inputLayer=imageInputLayer(imageSize)
inputLayer = ImageInputLayer with properties: Name: " InputSize: [32 32 3] Hyperparameters dataugmentation: 'none' NormalizationDimension: 'auto' Mean: []

接下来,定义网络的中间层。中间层由重复的卷积块、ReLU(整流线性单元)和池化层组成。这三层构成了卷积神经网络的核心构建块。卷积层定义了滤波器权值集,这些权值集在网络训练时更新。ReLU层将非线性添加到网络中,允许网络逼近非线性函数,将图像像素映射到图像的语义内容。当数据流经网络时,池层向下采样数据。在一个有很多层的网络中,应该谨慎地使用池层,以避免过早地对网络中的数据进行降采样。

%卷积层参数filterSize=[5];numFilters=32;middleLayers=[%第一个卷积层有一组32个5x5x3滤波器。a% 2像素的对称填充被添加,以确保图像边界%包括在处理过程中。这是必须避免的边界上的信息过早地被冲走了%网络。Convolution2Dlayer(过滤,NumFilters,'填充'2)%请注意,过滤器的第三维可以省略,因为它%根据网络的连通性自动推断。在里面%这种情况下,因为该层跟随图像层,第三层%维度必须为3,以匹配输入中的通道数量% 图片。%next添加Relu层:reluLayer()%后面是一个最大池化层,有一个3x3的空间池区域%和2个像素的步幅。这是对数据维度的向下采样% 32x32至15x15。maxPooling2dLayer (3“大步走”2)%重复3个核心层以完成网络的中间部分。Convolution2Dlayer(过滤,NumFilters,'填充',2)reluLayer()maxPooling2dLayer(3,“大步走”,2)卷积2dlayer (filterSize,2 * numFilters,'填充',2)reluLayer()maxPooling2dLayer(3,“大步走”,2) ]
middleelayers = 9x1 Layer array with layers:1”卷积32 5 x5旋转步[1]和填充2 2 2 2 2”ReLU ReLU 3”麦克斯池3 x3马克斯池步(2 - 2)和填充(0 0 0 0)4”卷积32 5 x5旋转步[1]和填充(2 2 2 2)5”ReLU ReLU 6”马克斯池3 x3马克斯池步(2 - 2)和填充[0 0 0 0]7“卷积64maxpooling 3x3 Max Pooling with stride [2 2] and padding [0 0 0 0]

通过重复这3个基本层,可以创建更深层次的网络。但是,应减少池层的数量,以避免过早地对数据进行下采样。网络早期的下采样丢弃了对学习有用的图像信息。

CNN的最后一层通常由完全连接层和软最大损失层组成。

finalLayers = [%添加一个具有64个输出神经元的完全连接层。的输出大小这一层将是一个长度为64的数组。fullyConnectedLayer (64)%添加一个ReLU非线性。雷卢耶%添加最后完全连接的图层。此时,网络必须%产生10个信号,可用于测量输入图像是否正确%属于这一类或那一类。这种测量是用%后续损耗层。fullyConnectedLayer(numImageCategories)%增加softmax loss层和分类层。最后的图层使用%输出的全连接层计算的范畴图像类上的概率分布。在培训期间%在这个过程中,所有的网络权重都会被调整,以最小化在此过程中的损失%的分布。softmaxLayer classificationLayer]
finalLayers = 5x1 Layer array with layers: 1 " Fully Connected 64 Fully Connected Layer 2 " ReLU ReLU 3 " Fully Connected 10 Fully Connected Layer 4 " Softmax Softmax 5 " Classification Output crossentropyex . txt . txt . txt

结合输入,中间和最终层。

图层=[inputLayer middleLayers finalLayers]
图层= 15x1层阵列,带有图层:1''图像输入32x32x3图像与“Zerocenter”归一化2''''卷积32 5x5卷绕卷曲[1 1]和填充[2 2 2 2] 3''relu Relu 4''max汇集3x3 max汇集步进[2 2]并填充[0 0 0] 5''卷积32 5x5带脚步的卷曲[1 1]和填充[2 2 2 2] 6'relu Relu 7''最大池3x3最大汇集步幅[2 2]和填充[0 0 0 0] 8''卷积64 5x5卷曲与步幅[1 1]和填充[2 2 2 2] 9''relu Relu 10''最大池池3x3 max池梯长[2]和填充[0 0 0 0] 11''完全连接64个完全连接的层12''Relu Relu 13''完全连接的10完全连接的层14''Softmax Softmax 15''分类输出CrossentRopyex

使用正常分布的随机数初始化第一卷积层权重,标准偏差为0.0001。这有助于提高培训的收敛性。

层(2)。权重= 0.0001 * randn([filterSize numChannels numFilters]);

使用CIFAR-10数据训练CNN

既然网络架构定义了,它可以使用CIFAR-10训练数据训练。首先,使用该设置网络培训算法trainingOptions(深度学习工具箱)函数。网络训练算法使用动量随机梯度下降(SGDM),初始学习率为0.001。训练期间,初始学习率每8个历元降低一次(1个历元定义为通过整个训练数据集的一次完整过程)。训练算法运行40个历元。

请注意,训练算法使用128个图像的最小批量大小。如果使用GPU进行训练,由于GPU上的内存限制,此大小可能需要降低。

%设置网络培训选项选择= trainingOptions ('sgdm',...“动力”, 0.9,...“初始学习率”, 0.001,...'shownrateschedule',“分段”,...“LearnRateDropFactor”, 0.1,...“LearnRateDropPeriod”8...“L2Regularization”, 0.004,...“MaxEpochs”, 40,...'minibatchsize', 128,...'verbose',真正的);

训练网络使用列车网络(深度学习工具箱)函数。这是一个计算密集型的过程,需要20-30分钟才能完成。为了在运行此示例时节省时间,从磁盘加载了一个经过预训练的网络。如果您希望自己培训网络,请设置溺爱变量为true。

请注意,支持CUDA的NVIDIA™ 强烈建议使用GPU进行培训。

%从磁盘加载经过培训的网络,以节省运行时的时间% 例子。将此标志设置为true以培训网络。doTraining = false;如果溺爱%训练一个网络。Cifar10Net = Trainnetwork(StrafterImages,培训标签,层,选择);其他的%以预先训练好的探测器为例。负载(“rcnnStopSigns.mat”,“cifar10Net”)终止

验证CIFAR-10网络培训

训练网络后,应验证网络以确保训练成功。首先,快速可视化第一个卷积层的滤波器权重有助于识别训练中的任何直接问题。

%提取第一卷积层权重w = cifar10Net.Layers (2) .Weights;%重新缩放权重到范围[0,1]以更好地显示w = Rescale(W);图蒙太奇(W)

第一层权重应具有一些定义良好的结构。如果权重看起来仍然是随机的,则表明网络可能需要额外的训练。在这种情况下,如上所示,第一层过滤器已从CIFAR-10训练数据中学习了边缘特征。

为了完全验证训练结果,使用CIFAR-10测试数据测量网络的分类精度。低准确度分数表示需要额外的培训或额外的培训数据。本示例的目标不一定是在测试集上实现100%的准确度,而是充分训练网络以用于训练目标检测器。

%在测试集中运行网络。YTest =分类(cifar10Net, testestimages);%计算精度。精度=总和(YTest==testLabels)/numel(testLabels)
精度=0.7456

进一步的训练将提高精度,但这对于训练R-CNN目标检测器来说是不必要的。

负荷训练数据

既然网络在CIFAR-10分类任务中运行良好,那么迁移学习方法可以用于对网络进行微调,用于停止符号检测。

首先加载停车标志的地面真实数据。

%加载地面实况数据数据=负载('stopsignsandcars.mat',“stopSignsAndCars”);stopSignsAndCars=data.stopSignsAndCars;%更新图像文件的路径以匹配本地文件系统visiondata = fullfile (toolboxdir (“愿景”),'VisionData');stopSignsAndCars.imageFilename=fullfile(visiondata,stopSignsAndCars.imageFilename);%显示地面真实数据的摘要摘要(停车标志和车辆)
变量:imageFilename:41×1单元格字符向量数组stopSign:41×1单元格carRear:41×1单元格carFront:41×1单元格

培训数据包含在包含图像文件名和ROI标签的表中,用于停车标志,汽车前线和后部。每个ROI标签都是图像内的感兴趣对象的边界框。对于训练停止标识探测器,只需要停止标志ROI标签。必须删除汽车前方和后部的投资回报标签:

%只保留图像文件名和停止标志ROI标签stopSigns = stopSignsAndCars(:, {)“imageFilename”,“停车标志”});%显示一个训练图像和地面真实边界框I=imread(stopSigns.imageFilename{1});I=insertObjectAnnotation(I,“矩形”,stopsigns.stopsign {1},“停车标志”,'行宽'8);图imshow(我)

注意,在这个数据集中只有41张训练图像。只用41幅图像从头开始训练R-CNN对象检测器是不实际的,也不会产生一个可靠的停止标志检测器。因为停止标志检测器是通过微调一个网络来训练的,这个网络已经在一个更大的数据集上预先训练过(CIFAR-10有50,000张训练图像),所以使用一个更小的数据集是可行的。

火车R-CNN停车标志检测器

最后,使用trainRCNNObjectDetector. 该功能的输入是地面真值表,其中包含标记的停车标志图像、预先训练的CIFAR-10网络和训练选项。培训功能自动将原始的CIFAR-10网络(将图像分为10类)修改为一个可以将图像分为两类的网络:停车标志和一般背景类。

在培训期间,使用从地面真实数据中提取的图像补丁进行微调,输入网络权重。“PositionOverlaprange”和“负极源性”参数控制,图像贴片用于培训。正面训练样本是与地面真理盒重叠0.5到1.0的训练样本,通过联盟度量的边界箱交叉来测量。负训练样本是那些重叠0到0.3的样本。应通过在验证集上测试培训的检测器来选择这些参数的最佳值。

R-CNN培训,强烈建议使用MATLAB工作者的并行池,以减少培训时间trainRCNNObjectDetector自动创建和使用一个并行池基于您的平行的偏好设置.确保在培训之前启用并行池的使用。

为了在运行此示例时节省时间,从磁盘加载了一个经过预训练的网络。如果您希望自己培训网络,请设置溺爱变量为true。

请注意,支持CUDA的NVIDIA™ 强烈建议使用GPU进行培训。

%从磁盘加载经过培训的探测器,以节省运行探测器时的时间% 例子。将此标志设置为true以培训探测器。doTraining = false;如果溺爱设置培训选项选项=培训选项('sgdm',...'minibatchsize', 128,...“初始学习率”1 e - 3,...'shownrateschedule',“分段”,...“LearnRateDropFactor”, 0.1,...“LearnRateDropPeriod”,100,...“MaxEpochs”,100,...'verbose',真正的);%训练一个R-CNN目标探测器。这需要几分钟。rcnn=列车RCNNObjectDetector(停车标志、cifar10Net、选项、,...“负超范围”, 0.3 [0],“正超范围”,[0.5 1])其他的%为示例加载预先训练的网络。负载(“rcnnStopSigns.mat”,“rcnn”)终止

测试R-CNN停止标志检测器

R-CNN物体探测器现在可以用来检测图像中的停车标志。在测试图像上试试:

读取测试图像testImage=imread('stopsigntest.jpg');%检测停止标志[B盒、分数、标签]=检测(rcnn、测试图像、,'minibatchsize',128)
bboxes =1×4419 147 31 20
得分=0.9955
标签=明确的分类停止标志

R-CNN对象探测方法为每个检测返回对象边界框、检测分数和类标签。当检测多个物体时,如停车、让行或限速标志时,标签非常有用。分数介于0和1之间,表示检测的置信度,可用于忽略低分数检测。

%显示检测结果[得分,Idx] = Max(得分);bbox = bboxes(idx,:);注释= sprintf(“%s:(置信度=%f)”标签(idx),得分);outputImage = insertObjectAnnotation (testImage,“矩形”,bbox,annotation);图imshow(输出图像)

调试提示

R-CNN探测器内使用的网络也可用于处理整个测试图像。通过直接处理大于网络输入大小的整个图像,可以生成分类分数的二维热图。这是一个有用的调试工具,因为它有助于识别映像中混淆网络的项目,并有助于深入了解如何改进培训。

%训练后的网络存储在R-CNN检测器中rcnn.network.
ans=具有以下属性的系列网络:层:[15×1 nnet.cnn.layer.layer]

提取激活(深度学习工具箱)从软MAX层,这是网络中的第14层。这些是网络产生的分类分数,因为它扫描图像。

(rcnn featureMap =激活。网络testImage 14);% softmax激活被存储在一个三维数组中。尺寸(特征图)
ans=1×343 78 2

featureMap中的第三维对应于对象类。

rcnn。一会
ans=2×1细胞{' stopSign}{‘背景’}

停车标志特征图存储在第一个通道中。

stopSignMap=featureMap(:,:,1);

由于网络中的下采样操作,激活输出的大小小于输入图像。要生成更好的可视化效果,请调整大小停车标志图到输入图像的大小。这是一个非常粗略的近似,将激活映射到图像像素,仅用于说明目的。

%调整stopSignMap的大小以实现可视化[高度,宽度,〜] =尺寸(testimage);stopsignmap = imresize(stopsignmap,[高度,宽度]);%可视化特征图叠加在测试图像上。featuremaponimage = imfuse(testimage,stopsignmap);图imshow(featuremaponimage)

测试图像中的停止标志与网络激活的最大峰值很好地对应。这有助于验证R-CNN探测器内使用的CNN是否有效地识别停车标志。如果出现其他峰值,这可能表明培训需要额外的负面数据来帮助防止误报。如果是这种情况,那么您可以在训练选项中增加“MaxEpochs”并重新训练。

总结

这个例子展示了如何使用CIFAR-10数据训练的网络来训练R-CNN停止标志物体检测器。使用深度学习也可以采用类似的步骤来训练其他目标检测器。

参考文献

[1] Girshick,R.,J.Donahue,T.Darrell和J.Malik.“用于精确目标检测和语义分割的丰富特征层次。”2014年IEEE计算机视觉和模式识别会议的诉讼程序.哥伦布,哦,2014年6月,第580-587页。

邓娇,董伟,索切尔,吕丽君。Li, K. Li和L. Fei-Fei。ImageNet:一个大规模的分级图像数据库。2009年IEEE计算机视觉与模式识别会议论文集. 佛罗里达州迈阿密,2009年6月,第248-255页。

Krizhevsky, A.和G. Hinton“从微小图像中学习多层特征。”硕士论文。多伦多大学,多伦多,加拿大,2009。

[4] https://code.google.com/p/cuda-convnet/

另见

|(深度学习工具箱)|(深度学习工具箱)||||||(深度学习工具箱)||(深度学习工具箱)

相关的话题