将数字识别神经网络转换为定点并生成C代码
这个例子展示了如何使用定点工具和查找表优化器将Simulink™中的神经网络分类模型转换为定点。金宝app转换之后,您可以使用Simulink Coder生成C代码。金宝app
概述
使用定点工具,您可以将设计从浮点转换为定点。使用查找表优化器为无界函数生成内存高效的查找表替换,例如经验值
和log2
。使用这些工具,本示例展示了如何将训练好的浮点神经网络分类模型转换为使用嵌入式高效的定点数据类型。
数字分类和MNIST数据集
MNIST手写数字数据集是神经网络领域常用的数据集。有关使用此数据集创建双层神经网络的简单方法的示例,请参见初学者人工神经网络。
数据和神经网络训练
根据指南下载培训和测试MNIST文件初学者人工神经网络。加载数据并训练网络。
%加载数据Tr = csvread()“train.csv”, 1,0);%读取train.csvSub = csvread()“test.csv”, 1,0);%读取test.csv%准备数据N = size(tr, 1);数据集中样本数的%target = tr(:,1);%第一列是|标签|目标(目标== 0)= 10;%用“10”表示“0”Targetsd = dummyvar(目标);%将标签转换为虚拟变量输入= tr(:,2:end);%其余列是预测符输入=输入';转置输入%目标=目标';转置目标Targetsd = Targetsd ';%转置哑变量rng (1);再现性%C = cvpartition(n,“坚持”、n / 3);%保留数据集的1/3Xtrain = inputs(:, training(c));% 2/3的投入用于培训Ytrain = targetsd(:, training(c));%培训目标的2/3Xtest = inputs(:, test(c));% 1/3的输入用于测试Ytest = targets(test(c));%目标的1/3用于测试Ytestd = targetsd(:, test(c));% 1/3用于测试的虚拟变量%列车网络hiddenLayerSize = 100;net = patternnet(hiddenLayerSize);[net, tr] = train(net, Xtrain, Ytrain);视图(净);输出= net(Xtest);errors = gsubtract(Ytest,输出);performance = perform(net, Ytest, output);图中,plotperform (tr);
关闭网络视图。
nnet.guis.closeAllViews ();
定点转换的模型准备
训练完网络后,使用gensim
从深度学习工具箱™功能生成一个Simulink模型。金宝app
Sys_name = gensim(net,“名字”,“mTrainedNN”);
生成的模型gensim
函数包含经过训练的权重和偏置的神经网络。通过在网络输出端启用信号记录,并添加输入刺激和验证块,准备训练好的神经网络转换为固定点。修改后的模型为fxpdemo_mnist_classification
。
打开并检查模型。
模型=“fxpdemo_mnist_classification”;System_under_design =[模型/模式识别神经网络];Baseline_output =[模型' / yarr '];open_system(模型);
要打开定点工具,右键单击函数拟合神经网络子系统并选择定点的工具
。或者,使用定点工具的命令行界面。固定点工具及其命令行界面帮助您准备转换模型,并将系统转换为固定点。您可以使用定点工具通过仿真和范围分析来收集模型中对象的范围和溢出测量。在本例中,使用定点工具的命令行界面将神经网络转换为定点。
converter = DataTypeWorkflow.Converter(system_under_design);
运行模拟以收集范围
用仪器模拟模型以收集范围。使用“使用双重覆盖收集范围”
快捷方式。保存模拟运行名称以供以后的步骤使用。
converter.applySettingsFromShortcut (“使用双重覆盖收集范围”);collect_ranges = converter.CurrentRunName;sim_out = converter.simulateSystem();
在转换之前绘制正确的分类率,以建立基线行为。
plotConfusionMatrix(sim_out, baseline_output, system_under_design,“转换前的分类率”);
提出定点数据类型
定点工具利用仿真得到的距离信息,对所设计系统中的块提出定点数据类型。在本例中,为了确保工具为子系统中的所有块提出签名数据类型,请禁用ProposeSignedness
选项中的ProposalSettings
对象。
ps = DataTypeWorkflow.ProposalSettings;转换器。proposeDataTypes (collect_ranges、ps);
应用建议的数据类型
默认情况下,定点工具应用所有建议的数据类型。使用applyDataTypes
方法来应用数据类型。如果您只想应用建议的子集,请在定点工具中使用接受复选框,以指定要应用的提案。
converter.applyDataTypes (collect_ranges);
验证数据类型
建议的类型应该正确处理所有可能的输入。将模型设置为使用新应用的类型进行模拟,对模型进行模拟,观察转换后的神经网络回归精度保持不变。
converter.applySettingsFromShortcut ('具有指定数据类型的范围集合');sim_out = converter.simulateSystem();
绘制定点模型的正确分类率。
plotConfusionMatrix(sim_out, baseline_output, system_under_design,“定点换算后的分类费率”);
用优化的查找表替换激活函数
要获得更高效的代码,请将第一层中的Tanh Activation函数替换为查找表或CORDIC实现。在本例中,使用查找表优化器获取要替换的查找表双曲正切
。在本例中,指定EvenPow2Spacing
为断点间距,以获得更快的执行速度。
Block_path = [system_under_design .“图层1 / tansig”];p = FunctionApproximation.Problem(block_path);p. options . wordlength = 16;p.Options.BreakpointSpecification =“EvenPow2Spacing”;Solution = p.solve;solution.replaceWithApproximate;
| | ID内存(位)| |可行的表大小|断点WLs | TableData西城| BreakpointSpecification |错误(Max、电流)| | 0 | 64 | 0 | 2 | 16 | | EvenPow2Spacing | 7.812500 e 03, 1.000000 e + 00 | | 1 | 8224 | 1 | 512 | 16 | | EvenPow2Spacing | 7.812500 e 03, 1.525879 e 03 | | 2 | 4128 | 1 | 256 | 16 | | EvenPow2Spacing | 7.812500 e 03, 5.981445 e 03 | | 3 | 2080 | 0 | 128 | 16 | | EvenPow2Spacing | 7.812500 e 03,2.331543e-02 |最佳解决方案| ID |内存(bits) |可行|表大小|断点WLs | TableData WL | BreakpointSpecification | Error(Max,Current) | | 2 | 4128 | 1 | 256 | 16 | 16 | EvenPow2Spacing | 7.812500e-03, 5.981445e-03 |
按照相同的步骤更换经验值
函数在softmax实现的第二层带有一个查找表。
Block_path = [system_under_design ./ 2层/ softmax /经验的];p = FunctionApproximation.Problem(block_path);p. options . wordlength = 16;p.Options.BreakpointSpecification =“EvenPow2Spacing”;
要获得优化的查找表,需要为输入定义有限的下界和上界。
p. inputlowbounds = -40;p.InputUpperBounds = 0;Solution = p.solve;solution.replaceWithApproximate;
| | ID内存(位)| |可行的表大小|断点WLs | TableData西城| BreakpointSpecification |错误(Max、电流)| | 0 | 64 | 0 | 2 | 16 | | EvenPow2Spacing | 7.812500 e 03, 9.996643 e-01 | | 1 | 2608 | 1 | 161 | 16 | | EvenPow2Spacing | 7.812500 e 03, 6.907394 e 03 | | 2 | 1328 | 0 | 81 | 16 | | EvenPow2Spacing | 7.812500 e 03,2.451896e-02 |最佳解决方案| ID |内存(bits) |可行|表大小|断点WLs | TableData WL | BreakpointSpecification | Error(Max,Current) | | 1 | 2608 | 1 | 161 | 16 | 16 | EvenPow2Spacing | 7.812500e-03, 6.907394e-03 |
用查找表近似值替换函数后验证模型准确性。
converter.applySettingsFromShortcut (converter.ShortcutsForSelectedSystem {2});sim_out = converter.simulateSystem;plotConfusionMatrix(sim_out, baseline_output, system_under_design,“功能替换后的分类率”);
生成C代码
要生成C代码,右键单击函数拟合神经网络子系统,选择C/ c++代码>构建子系统
。单击构建按钮,提示可调参数。
参考文献
[1] LeCun, Y., C. Cortes,和C. J. C. Burges。“MNIST手写数字数据库。”http://yann.lecun.com/exdb/mnist/。