这个例子展示了如何使用一个数据集来找出激活深层神经网络的渠道。这允许您了解神经网络的工作原理和诊断潜在问题与一个训练数据集。
这个示例介绍了很多简单的可视化技术,使用GoogLeNet transfer-learned食品数据集。通过观察图像最大或最小激活分类器,你会发现一个神经网络分类为什么错了。
加载图像作为图像数据存储。这个小数据集包含一个共有978个观测与9类的食物。
这个数据分割成一个培训、验证和测试集准备转移使用GoogLeNet学习。显示选择的图像数据集。
rng默认的dataDir = fullfile (tempdir,“食品数据集”);url =“//www.tatmou.com/金宝appsupportfiles/nnet/data/ExampleFoodImageDataset.zip”;如果~存在(dataDir“dir”mkdir (dataDir);结束downloadExampleFoodImagesData (url, dataDir);
下载MathWorks例子食物图像数据集…这可能需要几分钟时间下载…下载完成了…将文件解压缩……解压缩完成……完成了。
imd = imageDatastore (dataDir,…“IncludeSubfolders”,真的,“LabelSource”,“foldernames”);[imdsTrain, imdsValidation imdsTest] = splitEachLabel (imd, 0.6, 0.2);rnd = randperm(元素个数(imds.Files), 9);为i = 1:元素个数(rnd)次要情节(3 3 i) imshow (imread (imds.Files {rnd (i)}))标签= imds.Labels (rnd (i));标题(标签,“翻译”,“没有”)结束
再次使用pretrained GoogLeNet网络和训练它分类的9种食物。如果你没有深度学习工具箱™模型GoogLeNet网络金宝app支持包安装,软件提供了一个下载链接。
尝试不同的pretrained网络,打开这个例子在MATLAB®和选择一个不同的网络,如squeezenet
一个网络,甚至超过googlenet
。所有可用网络列表,请参阅Pretrained深层神经网络。
网= googlenet;
的第一个元素层
网络的属性是图像输入层。这一层需要输入的图像大小224 - 224 - 3,3是颜色通道的数量。
inputSize = net.Layers (1) .InputSize;
网络的卷积层提取图像特征,最后可学的一层一层和最后的分类使用对输入图像进行分类。这两个层,“loss3-classifier”
和“输出”
GoogLeNet,包含的信息如何结合网络特性,提取类概率,损失价值,预测标签。火车pretrained网络分类的新图像,用新的替换这两个层层适应新的数据集。
从训练网络提取层图。
lgraph = layerGraph(净);
在大多数网络,可学的重量的最后一层是一个完全连接层。用一个新的替换这个完全连接层完全连接层与输出的数量等于类的数量在新数据集(9,在本例中)。
numClasses =元素个数(类别(imdsTrain.Labels));newfclayer = fullyConnectedLayer (numClasses,…“名字”,“new_fc”,…“WeightLearnRateFactor”10…“BiasLearnRateFactor”10);lgraph = replaceLayer (lgraph net.Layers (end-2) . name, newfclayer);
网络的分类层指定输出类。用一个新的替换分类层没有类标签。trainNetwork
自动设置输出类层的训练时间。
newclasslayer = classificationLayer (“名字”,“new_classoutput”);lgraph = replaceLayer (lgraph net.Layers(结束). name, newclasslayer);
网络需要输入的图像大小224 - 224 - 3,但图像的图像数据存储有不同的大小。使用一个增强图像数据存储图像自动调整训练。指定额外增加操作执行培训图片:随机翻转训练图像沿垂直轴,随机将其30像素,和规模10%的水平和垂直。数据增加有助于防止网络过度拟合和记忆的训练图像的细节。
pixelRange = 30 [-30];scaleRange = (0.9 - 1.1);imageAugmenter = imageDataAugmenter (…“RandXReflection”,真的,…“RandXTranslation”pixelRange,…“RandYTranslation”pixelRange,…“RandXScale”scaleRange,…“RandYScale”,scaleRange);augimdsTrain = augmentedImageDatastore (inputSize (1:2), imdsTrain,…“DataAugmentation”,imageAugmenter);
自动调整验证图像不执行进一步的数据,使用一个增强的图像数据存储不指定任何额外的预处理操作。
augimdsValidation = augmentedImageDatastore (inputSize (1:2), imdsValidation);
指定培训选项。集InitialLearnRate
小价值放慢学习的传输层没有冻结。在前面的步骤中,您过去可学的学习速率因子层增加加速学习在新的最后一层。这种组合的学习速率设置新层,导致快速学习慢学习在中间层,也没有学习在前面,冻层。
指定数量的时代列车。当执行转移学习,你不需要训练尽可能多的时代。一个时代是一个完整的培训周期在整个训练数据集。指定mini-batch大小和验证数据。计算每个时代精度验证一次。
miniBatchSize = 10;valFrequency =地板(元素个数(augimdsTrain.Files) / miniBatchSize);选择= trainingOptions (“个”,…“MiniBatchSize”miniBatchSize,…“MaxEpochs”4…“InitialLearnRate”3的军医,…“洗牌”,“every-epoch”,…“ValidationData”augimdsValidation,…“ValidationFrequency”valFrequency,…“详细”假的,…“阴谋”,“训练进步”);
使用训练数据训练网络。默认情况下,trainNetwork
使用GPU如果一个是可用的。这需要并行计算工具箱™和支持GPU设备。金宝app支持设备的信息,请参阅金宝appGPU的金宝app支持版本(并行计算工具箱)。否则,trainNetwork
使用一个CPU。您还可以指定使用的执行环境“ExecutionEnvironment”
名称-值对的观点trainingOptions
。这个数据集很小,因为培训是快。如果你运行这个例子和训练网络,你会得到不同的结果和随机性引起的误分类参与培训过程。
网= trainNetwork (augimdsTrain、lgraph选项);
使用精确的测试图像进行分类网络和计算分类精度。
augimdsTest = augmentedImageDatastore (inputSize (1:2), imdsTest);[predictedClasses, predictedScores] =(网络,augimdsTest)进行分类;精度=意味着(predictedClasses = = imdsTest.Labels)
精度= 0.8418
情节的混淆矩阵测试集预测。这突显出特定类导致网络的大多数问题。
图;confusionchart (imdsTest.Labels predictedClasses,“归一化”,“row-normalized”);
混淆矩阵表明,网络对某些类表现不佳,如希腊色拉、生鱼片,热狗,和寿司。这些类是弱势的数据集可能会影响网络性能。调查这些类之一,为了更好地理解为什么网络是艰难的。
图();直方图(imdsValidation.Labels);甘氨胆酸ax = ();ax.XAxis。TickLabelInterpreter =“没有”;
调查网络寿司类分类。
首先,找到图像的寿司寿司类最强烈激活网络。这回答了这个问题“哪个图像网络认为最sushi-like吗?”。
绘制maximally-activating图像,这些输入图像强烈激活全层的神经元“寿司”。此图显示了前4张图片,在下行类分数。
chosenClass =“寿司”;classIdx =找到(net.Layers(结束)。类= = chosenClass);numImgsToShow = 4;[sortedScores, imgIdx] = findMaxActivatingImages (imdsTest、chosenClass predictedScores, numImgsToShow);图plotImages (imdsTest imgIdx、sortedScores predictedClasses, numImgsToShow)
是寿司的网络关注正确的事情吗?maximally-activating寿司类的图像网络类似于彼此,很多轮形状聚集紧密地结合在一起。
网络在分类这些种类的寿司。然而,确认这是真的,为了更好地理解为什么网络使其决策,使用一个可视化技术像Grad-CAM。使用Grad-CAM更多信息,请参阅Grad-CAM揭示了深度学习的决定背后的原因。
阅读第一个缩放图像增强的图像数据存储,然后情节Grad-CAM可视化使用gradCAM
。
imageNumber = 1;观察= augimdsTest.readByIndex (imgIdx (imageNumber));img = observation.input {1};标签= predictedClasses (imgIdx (imageNumber));分数= sortedScores (imageNumber);gradcamMap = gradCAM(净、img标签);图α= 0.5;plotGradCAM (img, gradcamMapα);(标签)+ sgtitle(字符串”(分数:+马克斯(分数)+“)”)
Grad-CAM地图确认网络关注的寿司的形象。但是你也可以看到,网络是看的部分板块和表。
第二个图片的左边的寿司和一个孤独的寿司在右边。看看网络关注,读第二Grad-CAM形象和情节。
imageNumber = 2;观察= augimdsTest.readByIndex (imgIdx (imageNumber));img = observation.input {1};标签= predictedClasses (imgIdx (imageNumber));分数= sortedScores (imageNumber);gradcamMap = gradCAM(净、img标签);图plotGradCAM (img, gradcamMapα);(标签)+ sgtitle(字符串”(分数:+马克斯(分数)+“)”)
网络分类这寿司的形象,因为它看到一群寿司。然而,它是能够自行分类一个寿司吗?测试这个通过观察一个寿司的照片。
img = imread (strcat (tempdir,“食品数据集/寿司/ sushi_18.jpg”));img = imresize (img net.Layers (1) .InputSize (1:2),“方法”,“双线性”,“抗锯齿”,真正的);(标签,分数)=(净,img)进行分类;gradcamMap = gradCAM(净、img标签);图α= 0.5;plotGradCAM (img, gradcamMapα);(标签)+ sgtitle(字符串”(分数:+马克斯(分数)+“)”)
网络能够正确分类这个孤独的寿司。然而,GradCAM表明网络关注的寿司和黄瓜的集群,而不是整个拼凑。
运行Grad-CAM可视化技术在一个孤独的寿司,不包含任何堆小块的成分。
img = imread (“crop__sushi34-copy.jpg”);img = imresize (img net.Layers (1) .InputSize (1:2),“方法”,“双线性”,“抗锯齿”,真正的);(标签,分数)=(净,img)进行分类;gradcamMap = gradCAM(净、img标签);图α= 0.5;plotGradCAM (img, gradcamMapα);标题(string(标签)+”(分数:+马克斯(分数)+“)”)
在这种情况下,可视化技术突出网络表现不佳的原因。它错误地分类寿司的形象作为一个汉堡包。
为了解决这个问题,你必须养活更多的图片的网络训练过程中孤独的寿司。
现在发现这寿司寿司类激活网络的图像。这回答了这个问题“网络认为少sushi-like哪个图片?”。
这是有用的,因为它发现的图像网络表现糟糕,它提供了一些洞察其决定。
chosenClass =“寿司”;numImgsToShow = 9;[sortedScores, imgIdx] = findMinActivatingImages (imdsTest、chosenClass predictedScores, numImgsToShow);图plotImages (imdsTest imgIdx、sortedScores predictedClasses, numImgsToShow)
为什么网络分类寿司生鱼片?网络分类3的9图像作为生鱼片。其中的一些图片,例如图像4和9,实际上包含生鱼片,这意味着网络并不是分类。这些图片是贴错了标签。
看看网络关注,运行Grad-CAM技术在这些图像之一。
imageNumber = 4;观察= augimdsTest.readByIndex (imgIdx (imageNumber));img = observation.input {1};标签= predictedClasses (imgIdx (imageNumber));分数= sortedScores (imageNumber);gradcamMap = gradCAM(净、img标签);图α= 0.5;plotGradCAM (img, gradcamMapα);标题(string(标签)+”(寿司分数:+马克斯(分数)+“)”)
正如预期的那样,网络关注的是生鱼片的寿司。
为什么网络分类寿司披萨?网络图像的分类四个披萨,而不是寿司。考虑图1,这张图片有一个五颜六色的浇头,可能混淆了网络。
看到的哪一部分图像网络看,运行Grad-CAM技术在这些图像之一。
imageNumber = 1;观察= augimdsTest.readByIndex (imgIdx (imageNumber));img = observation.input {1};标签= predictedClasses (imgIdx (imageNumber));分数= sortedScores (imageNumber);gradcamMap = gradCAM(净、img标签);图α= 0.5;plotGradCAM (img, gradcamMapα);标题(string(标签)+”(寿司分数:+马克斯(分数)+“)”)
网络强烈关注的浇头。帮助网络区分披萨和寿司浇头,添加更多的训练图像与配料的寿司。网络也关注的板块。这可能是随着网络已经学会把某些食物和某些类型的盘子,寿司时还强调了看图片。改善网络的性能,火车上使用更多的例子的食物不同类型的盘子。
为什么网络分类寿司一个汉堡包吗?看看网络关注,运行Grad-CAM技术更进一步的形象。
imageNumber = 2;观察= augimdsTest.readByIndex (imgIdx (imageNumber));img = observation.input {1};标签= predictedClasses (imgIdx (imageNumber));分数= sortedScores (imageNumber);gradcamMap = gradCAM(净、img标签);图α= 0.5;plotGradCAM (img, gradcamMapα);标题(string(标签)+”(寿司分数:+马克斯(分数)+“)”)
网络是关注花的形象。色彩鲜艳的紫色的花和棕色茎已经混淆网络为确定这张照片作为一个汉堡包。
为什么网络分类寿司薯条?网络分类第三形象薯条代替寿司。这个特定的寿司有黄色的浇头,网络可能会把这种颜色和炸薯条。
这张图片上运行Grad-CAM。
imageNumber = 3;观察= augimdsTest.readByIndex (imgIdx (imageNumber));img = observation.input {1};标签= predictedClasses (imgIdx (imageNumber));分数= sortedScores (imageNumber);gradcamMap = gradCAM(净、img标签);图α= 0.5;plotGradCAM (img, gradcamMapα);标题(string(标签)+”(寿司分数:+马克斯(分数)+“)”,“翻译”,“没有”)
网络关注黄色寿司分类炸薯条。像汉堡一样,不寻常的颜色造成了网络分类的寿司。
帮助网络在这个特定的例子中,训练它有更多图片的黄色食品不是薯条。
调查越来越多,引起大或小类分数,和越来越多的网络分类自信但不正确,是一个简单的技巧可以提供有用的见解训练网络是如何运作的。在食物的情况下的数据集,这个例子强调:
测试数据包含几个图像正确真实的标签,如“生鱼片”实际上是“寿司”。数据也包含不完整的标签,如图像含有寿司和生鱼片。
网络认为“寿司”“多个集群,圆形的东西”。然而,它必须能够区分一个孤独的寿司。
任何与浇头寿司和生鱼片或不寻常的颜色混淆网络。要解决这个问题,数据必须有一个广泛的各种各样的寿司和生鱼片。
提高性能的网络需要看到更多的弱势阶层的照片。
函数dataDir downloadExampleFoodImagesData (url)%下载示例食物图像数据集,包含978的图像%不同类型的食物分为9类。% 2019年版权MathWorks公司。文件名=“ExampleFoodImageDataset.zip”;fileFullPath = fullfile (dataDir,文件名);% . zip文件下载到一个临时目录中。如果~存在(fileFullPath“文件”)流(“下载MathWorks例子食物图像数据集…\ n”);流(“这可能花费几分钟下载…\ n”);websave (fileFullPath、url);流(“下载完成…\ n”);其他的流(“跳过下载,文件已经存在…\ n”);结束%解压该文件。%%检查文件是否已经被检查存在解压缩%的类目录。exampleFolderFullPath = fullfile (dataDir,“披萨”);如果~存在(exampleFolderFullPath“dir”)流(“将文件解压缩…\ n”);解压缩(fileFullPath dataDir);流(“解完成…\ n”);其他的流(“跳过压缩,文件已经解压缩…\ n”);结束流(“完成。\ n”);结束函数[sortedScores, imgIdx] = findMaxActivatingImages (imd,类名,predictedScores numImgsToShow)%的预测成绩选择类所有的图像选择类%(如预测分数对寿司寿司的所有图片)[scoresForChosenClass, imgsOfClassIdxs] = findScoresForChosenClass (imd,类名,predictedScores);%的分数降序排序[sortedScores, idx] =排序(scoresForChosenClass,“下”);%返回只有前几的指标imgIdx = imgsOfClassIdxs (idx (1: numImgsToShow));结束函数[sortedScores, imgIdx] = findMinActivatingImages (imd,类名,predictedScores numImgsToShow)%的预测成绩选择类所有的图像选择类%(如预测分数对寿司寿司的所有图片)[scoresForChosenClass, imgsOfClassIdxs] = findScoresForChosenClass (imd,类名,predictedScores);%的分数按升序排序[sortedScores, idx] =排序(scoresForChosenClass,“提升”);%返回只有前几的指标imgIdx = imgsOfClassIdxs (idx (1: numImgsToShow));结束函数[scoresForChosenClass, imgsOfClassIdxs] = findScoresForChosenClass (imd,类名,predictedScores)%的指数类名(如。“寿司”是9类)uniqueClasses =独特(imds.Labels);chosenClassIdx =字符串(uniqueClasses) = =名称;%的指数在imageDatastore图像标签“名称”%(如找到所有的图像类寿司)imgsOfClassIdxs =找到(imd)。标签= =类名);%的预测成绩选择类的所有图像%选择类%(如预测分数对寿司寿司的所有图片)scoresForChosenClass = predictedScores (imgsOfClassIdxs chosenClassIdx);结束函数plotImages (imd, imgIdx sortedScores、predictedClasses numImgsToShow)为i = 1: numImgsToShow得分= sortedScores(我);sortedImgIdx = imgIdx(我);predClass = predictedClasses (sortedImgIdx);correctClass = imds.Labels (sortedImgIdx);imgPath = imds.Files {sortedImgIdx};如果predClass = = = correctClass颜色“{绿}\颜色”;其他的颜色={红}\颜色”;结束predClassTitle = strrep (string (predClass),“_”,' ');correctClassTitle = strrep (string (correctClass),“_”,' ');次要情节(装天花板(numImgsToShow. / 3), i) imshow (imread (imgPath));标题(预测:“+颜色+ predClassTitle +”{黑}\换行符\颜色得分:“+ + num2str(得分)“\ newlineGround真理:“+ correctClassTitle);结束结束函数plotGradCAM (img, gradcamMapα)次要情节(1、2、1)imshow (img);h =情节(1、2、2);imshow (img)在;显示亮度图像(gradcamMap“AlphaData”、α);originalSize2 =得到(h,“位置”);colormap飞机colorbar集(h,“位置”,originalSize2);持有从;结束
googlenet
|imageDatastore
|augmentedImageDatastore
|confusionchart
|dlnetwork
|分类
|occlusionSensitivity
|gradCAM
|imageLIME