将神经网络置于 Engee 功能块中¶
在本示例中,我们将把训练好的神经网络放在 Engee 画布上,作为一个块Engee Function
- 从中生成 Julia 上的代码。
任务描述¶
之前我们训练了一个全连接神经网络,根据两个输入变量$x_1$ 和$x_2$ 预测$y$ 的值。我们已经有了一个文件model.jld2
,训练好的神经网络就在其中。现在,我们将把它转化为 Julia 代码,并创建一个可用于任何模型的模块,或者创建我们自己的模块库。
⚠️ 在
Engee Function
代码块中只能使用全局寻址。因此,如果您的示例位于/user/start/data_analysis/neural_regression_to_engee_function
以外的文件夹中,您需要编辑块Engee Function
中的代码,写入文件neural_net_code.jl
的完整路径。
创建代码块掩码¶
在块的正面放置一些图画会很方便,这样可以简化模型的感知。我们将使用神经网络的拓扑结构作为遮罩。
我们需要ChainPlots
库,该库可为函数plot()
创建神经网络可视化 "配方",之后我们只需将神经网络作为参数传递给图形输出函数即可。
Pkg.add(["JLD2", "Flux", "ChainPlots", "Symbolics"])
using Flux, JLD2, ChainPlots
model = load_object( "$(@__DIR__)/model.jld2" ) # Загрузим нейросеть из файла
gr()
p = plot( model, titlefontsize=10, size=(300,300),
xticks=:none, series_annotations="", markersize=8,
markercolor="white", markerstrokewidth=4, linewidth=1 )
savefig( p, "$(@__DIR__)/neural_net_block_mask.png"); # Сохраним график в PNG
☝️ 在块掩码中已经规定了图片链接。但遮罩不会自动更新。要在图块面上加载插图,请打开其属性(在遮罩视图中)并点击 "更新遮罩"。
为神经网络创建 Julia 代码¶
Julia 语言的一个特点将帮助我们创建代码。
由于Flux
库完全是用 Julia 编写的,因此神经网络的每一层都由 Julia 代码描述。如果输入的不是数字,而是库Symbolics
中的数学符号,会发生什么情况呢?
using Symbolics
@variables x1 x2
s = model( [x1, x2] );
# Первые 200 символов этого кода
print( string(s[1])[1:200], "..." )
我们可以看到很多ifelse
...事实上,ReLU 激活的神经网络可以重写为一个大型片断线性函数。
让我们将代码保存为 .jl 文件¶
如果我们将代码保存在文本文件中,就可以通过include()
命令将其包含在程序块Engee Function
中,但只能是绝对地址。但您始终需要将该代码文件保存在模型文件夹中。还有另一种方法--将代码和掩码放在Engee Function
块中,使组件自给自足。
open("$(@__DIR__)/neural_net_code.jl", "w") do f
println(f, "function nn(x1, x2)\n $(s[1])\nend")
end
# Сразу же запустим этот код и получим прогноз нейросети:
include("$(@__DIR__)/neural_net_code.jl")
nn(1,2)
测试:从 Engee 功能块启动神经网络¶
让我们运行模型并将结果可视化。
# Загрузим (если модель еще не открыта) и выполним модель
if "neural_regression_to_engee_function" ∉ getfield.(engee.get_all_models(), :name)
engee.load( "$(@__DIR__)/neural_regression_to_engee_function.engee");
end
model_data = engee.run( "neural_regression_to_engee_function" );
# Подготовим выходные переменные
model_x1 = model_data["X1"].value;
model_x2 = model_data["X2"].value;
model_y = vec( hcat( model_data["Y"].value... ));
# Построим график
scatter!( model_x1, model_x2, model_y, ms=2.5, msw=.5, leg=false, zcolor=model_y, c=:viridis,
xlimits=(-3,3), ylimits=(-3,3), title="Прогноз от блока Engee Function", titlefont=font(10) )
我们看到的是一个熟悉的函数,但每个输出点都是由一个神经网络 "预测 "的,该网络经过训练,可以模拟我们需要的依赖关系$y = f(x_1, x_2)$ 。
结论¶
使用库Symbolics
生成 Julia 函数代码一点也不难,即使该函数是来自库Flux
的神经网络。只需选择一种方便的方式将代码放到画布上,就可以将神经网络作为面向模型的项目中的一个组件。