主要内容

激光雷达点云分割网络的代码生成

此示例显示如何为LIDAR语义分割生成深度学习网络的CUDA®MEX代码。此示例使用佩带的挤压ZeeSgvv2 [1]网络,该网络可以分段为属于三个类的组织激光雷云(背景, 和卡车)。有关网络培训程序的信息,请参阅LIDAR点云语义分割使用SCREEZESEGV2深层学习网络。生成的MEX代码将点云作为输入执行,并使用该点云执行预测Dagnetwork.SqueezeSegvv2网络的对象。

第三方先决条件

必需的

此示例生成CUDA MEX,并具有以下第三方要求。

  • 支持CUDA的NVIDIA®GPU和兼容驱动程序。

可选的

对于诸如静态,动态库或可执行文件的非MEX构建,此示例具有以下附加要求。

验证GPU环境

要验证编译器和运行此示例的库是否正确设置,请使用Coder.CheckGPuInstall.(GPU编码器)功能。

envCfg=coder.gpuEnvConfig('主持人');envcfg.deeplibtarget =“cudnn”;envcfg.deepcodegen = 1;Envcf​​g.quiet = 1;Coder.CheckGpuInstall(Envcf​​g);

分段网络

SqueezeSegV2是一种卷积神经网络(CNN)设计用于有组织的激光雷达点云的语义分割。它是一个在激光雷达数据集上训练并导入MATLAB®进行推理的深度编码器-解码器分割网络。在SqueezeSegV2中,编码器子网络由卷积层组成,卷积层中穿插着最大池层。这种排列顺序依次减少s输入图像的分辨率。解码器子网络由一系列转置卷积层组成,这些层依次提高输入图像的分辨率。此外,SqueezeSegV2网络通过包括上下文聚合模块(CAM)减轻丢失数据的影响.CAM是一个卷积子网络,具有值为[7,7]的filterSize,可从更大的感受域聚合上下文信息,从而提高网络对缺失数据的鲁棒性。本例中的SqueezeSegV2网络经过训练,可分割属于三类(背景、汽车和卡车)的点。

有关使用Mathworks Lidar DataSet在Matlab®中培训语义分段网络的更多信息,请参阅使用POINSEG深度学习网络的LIDAR点云语义分割

下载佩带的SqueezESEGv2网络。

net = getsqueezesegv2net();
正在下载预训练挤压SEGV2(2 MB)。。。

DAG网络包含238层,包括卷积,Relu和批量归一化层,以及焦损输出层。要显示深度学习网络架构的交互式可视化,请使用分析网络(深度学习工具箱)功能。

分析(网);

squeezesegv2_predict.入学点函数

挤压segv2_.m附加到此示例的入口点函数将点云作为输入,通过使用保存的深度学习网络对其执行预测squeezesegv2net.mat.函数从squeezesegv2net.mat.文件到持久变量中yeNet.并在后续预测调用中重用持久变量。

类型('screezesegvv2_predict.m');
函数OUT = SCREEZESEGV2_PREDICT(in)%#codegen%持久对象mynet用于加载DAG网络对象。在%第一次调用此函数时,构建持久对象并%设置。当调用该函数时随后的时间,同样的目的是%重复使用,以呼叫预测输入端上的,从而避免了重建和%重装网络对象。%Copyright 2020 MathWorks,Inc。持久性MyNet;如果是isempty(mynet)mynet = coder.loaddeeplearningnetwork('scriezesegv2net.mat');输入OUT中的最终%通过=预测(MYNET,IN);

生成CUDA MEX代码

为此生成CUDA MEX代码挤压segv2_.m入口点函数,为MeX目标创建GPU代码配置对象,并将目标语言设置为C++。coder.deeplearningconfig(GPU编码器)函数创建一个CUDNN.深度学习配置对象并将其分配给深度学习配置GPU代码配置对象的属性。跑过Codegen.命令,指定[64,1024,5]的输入大小。该值对应于挤压符号的输入层的大小。

cfg = coder.gpuconfig('mex');cfg.targetlang ='c ++';cfg.DeepLearningConfig=coder.DeepLearningConfig(“cudnn”);Codegen.-Config.CFG.squeezesegv2_predict.-  args.{ONE(64,1024,5,'UINT8')}-报告
代码成功:查看报告

若要生成利用Nvidia TunSRRT库的CUDA C++代码,请在代码中指定Coder.deeplearningconfig('tensorrt')代替Coder.DeeplearningConfig('CUDNN')

有关如何在英特尔®处理器上生成深度学习网络的MEX代码的信息,请参阅MKL-DNN的深度学习网络代码生成(MATLAB编码器)

准备数据

在MATLAB®中加载有组织的测试点云。将点云转换为五个通道图像以进行预测。

ptcloud =缺陷('outerlidardrivingdata.pcd');i = pointcloudtoimage(ptcloud);%检查转换的数据谁是一世
名称大小字节类属性I 64x1024x5 327680 uint8

图像有五个通道。这(x,y,z)点坐标包括前三个通道。第四通道包含LIDAR强度测量。第五频道包含计算为的范围信息 R. = X 2 + y 2 + Z. 2

可视化图像的强度通道。

intensityChannel=I(:,:,4);图;imshow(intensityChannel);标题(“强度图像”);

在数据上运行生成的mex

称呼squeezesegv2_predict_mex.在五通道图像上。

预测得分=挤压SEGV2预测mex(I);

预测大学分数变量是一个三维矩阵,它有三个通道,对应于每个类的像素级预测分数。使用最大预测分数计算通道以获得像素级标签

[〜,argmax] = max(predict_scores,[],3);

覆盖强度信道图像上的分段标签并显示分段区域。调整分段输出的大小并添加彩色键以获得更好的可视化。

类= [“背景”“车”“卡车”];cmap = lidarcolormap();segmentedimage = labeloverlay(InthenseShannel,Argmax,“彩色地图”,CMAP);segmentedimage = imresize(semmentedimage,“规模”, [2 1],“方法”“最近的”);数字;imshow(semmentedimage);n = numel(类);蜱= 1 /(n * 2):1 / n:1;彩色杆(“滴答声标签”,cellstr(类别),“滴答声”,蜱虫,“滴答声长度”,0,'ticklabelinterpreter''没有任何');Colormap(CMAP)标题(“语义分割结果”);

在点云序列上运行生成的mex代码

读取一个输入点云序列。该序列包含10个点云点云使用Ouster OS1 LIDAR传感器收集的框架。输入数据的高度为64和宽度为1024,因此每个PointCloud对象的尺寸为64到1024。

datafile ='highwayscenedata.mat';%在工作区中加载数据。加载(数据文件);

设置不同的颜色,可视化不同类别的点心标签。

%将颜色涂抹于汽车。carClassCar=0(6410243,'uint8');Carclasscar(:,:,1)= 255 *那些(64,1024,'uint8');%将颜色蓝色涂抹到卡车上。truckClassColor=0(64,1024,3,'uint8');truckClassColor(:,:,3)=255*one(641024,'uint8');%将颜色灰色应用于背景。backgroundclasscolor = 153 * =(64,1024,3,'uint8');

设定PCPlayer.函数属性以显示序列和输出预测。通过帧读取输入序列帧并使用模型检测感兴趣的类。

xlimits=[0 120.0];ylimits=[-80.7 80.7];zlimits=[-8.4 27];player=pcplayer(xlimits,ylimits,zlimits);set(get(player.Axes,'父母'),“单位”'标准化'“外置”,[0 0 1 1]); 缩放(获取)(player.Axes,'父母'),2);set(player.axes,'xcolor''没有任何'“YColor”'没有任何'“ZColor”'没有任何');为了i = 1:numel(inputdata)ptcloud = inputdata {i};%转换点云到五声道图像进行预测。i = pointcloudtoimage(ptcloud);%呼叫Squeezesegv2_predict_mex在5通道图像上。预测得分=挤压SEGV2预测mex(I);%将数字输出值转换为分类标签。[〜,predigeOutput] = max(predict_scores,[],3);predigeOutput =分类(predigeOutput,1:3,类);%从标签中提取索引。carIndices=预测输出==“汽车”;卡车里程=预计产量==“卡车”;backgressionIndices = predigeOutput =='背景';%提取每个类的点云。carpointcloud = select(ptcloud,carindices,'输出''满的');TruckPointCloud = Select(Ptcloud,Truckindices,'输出''满的'); backgroundPointCloud=选择(ptCloud、BackgroundIndex、,'输出''满的');%将颜色填充到不同的类别。CarpointCloud.Color = Carclasscar;TruckPointCloud.Color = TruckclassColor;BackgroundPointCloud.Color = backgroundClassColor;%合并并使用类信息添加所有已加工点云。COMENTCLOUD = PCMerge(CarpointCloud,TruckPointCloud,0.01);COMENTCLOUD = PCMerge(CornCloud,BackgroundPointCloud,0.01);%查看输出。视图(播放器,彩色云);drawnow;结尾

辅助函数

在此示例中使用的辅助功能遵循。

类型pointcloudtoimage.m.
函数image=pointCloudToImage(ptcloud)%pointCloudToImage将有组织的三维点云转换为5通道%2-D图像。图像=ptcloud.Location;图像(:,:,:,4)=ptcloud.Intensity;rangeData=IComputerRangeData(图像(:,:,1),图像(:,:,2),图像(:,,:,3));图像(,,,:,5)=范围数据;%转换为uint8。图像=uint8(图像);end%-------------------------------------------------------------函数rangeData=IComputerRangeData(xChannel,yChannel,zChannel)rangeData=sqrt(xChannel.*xChannel+yChannel.*yChannel+zChannel.*zChannel);结束
类型利达科洛玛
函数cmap=lidarColorMap()cmap=[0.00 0.00 0.00%背景0.98 0.00 0.00%汽车0.00 0.00%卡车];结束

参考

[1]吴,比辰,宣扬周,浙城赵,湘雅悦,和库尔特凯兹。“Screezesegv2:改进了LIDAR点云的道路对象分割的模型结构和无监督域适应。”预印刷品,2018年9月22日提交.thth://arxiv.org/abs/1809.08495。