MATLAB函数外部使用

Tim
2025-03-07
点 赞
0
热 度
40
评 论
0

文章摘要

智阅GPT

项目需要在C#中使用MATLAB函数,根据网上老哥提供的方案查阅资料并记录以下(有部分可能存在认知错误,后面遇到再改)

ArrayFire/ Armadillo

未尝试

C++库,对MATLAB函数进行逐句翻译,直接编译成dll。 效率最高(需要硬件支持)

ArrayFire

ArrayFire是一个通用的GPU计算库,旨在简化并行架构(如CPU、GPU和其他硬件加速设备)上的软件开发过程。该项目主要使用C++编写,但也提供了其他语言的API,如C、PythonFortran,以满足不同开发者的需求。 官方网站

Octave/Python

转Octave或者Python。 工作量最小,效率还行

Octave

下载地址

mkoctfile

未尝试

入参是 矩阵/张量,使用mkoctfile编译dll方便点

mkoctfile --link-stand-alone

Octave.NET

.NET拓展包。 仓库地址

Basics

基础使用:

//指定octave-cli.exe路径(可选) 
OctaveContext.OctaveSettings = new OctaveSettings() { OctaveCliPath = @"D:\GNU Octave\Octave-9.4.0\mingw64\bin\octave-cli.exe" };
 using (var octave = new OctaveContext())
 {
     // Please note that there is no ";" at the end. This is important if we want to capture the output.
     var scalarResult = octave
             .Execute("2 + 2")
             .AsScalar();

     var vectorResult = octave
         .Execute("[1 2 3 4 5]")
         .AsVector();

     var matrixResult = octave
         .Execute("[1 2 3 4 5; 5 4 3 2 1]")
         .AsMatrix();

     var vec = new double[] { 1, 2, 3, 4, 5 };
     var anotherVector = octave.Execute(vec.ToOctave()); // [1 2 3 4 5]

     var mat = new[]
     {
         new double[] { 1, 2, 3, 4, 5 },
         new double[] { 1, 2, 3, 4, 5 }
     };
     var anotherMatrix = octave.Execute(mat.ToOctave());// [1 2 3 4 5;1 2 3 4 5]
 }
DisplayPlot

显示图表:

using (var octave = new OctaveContext())
{
                // Note: your octave-cli must support some plot backend, in case of problems investigate manually in octave-cli

                var script = @"
x = -10:0.1:10;
y = sin (x);

handle = plot (x, y);

title (""Hello from C#"");
xlabel (""x"");
ylabel (""sin (x)"");

waitfor(handle); #                 <- without that plot window would not show 
                ";

                octave.Execute(script, int.MaxValue);
}
Packages

加载包:

using (var octave = new OctaveContext())
{
    octave.Execute("pkg load fuzzy-logic-toolkit;");
    double result = octave
        .Execute("algebraic_product(5,2)")
        .AsScalar(); // 10
}
引用外部.m文件

需要注意的是调用函数时结尾不要加分号octave.Execute("t1(6, 7)") 否则就抑制输出了,得用 disp() 显示

addpath 指定工作区:

//指定octave-cli.exe路径(可选) 
OctaveContext.OctaveSettings = new OctaveSettings() { OctaveCliPath = @"D:\GNU Octave\Octave-9.4.0\mingw64\bin\octave-cli.exe" };
 using (var octave = new OctaveContext())
 {
     string script = @"addpath('C:/Users/admin/Desktop/test');t1(6, 7)";

      // 调用 Octave 函数
      var sumResult = octave.Execute(script); 
 }
直接运算

在C#中运行Octave 代码:

//指定octave-cli.exe路径(可选) 
OctaveContext.OctaveSettings = new OctaveSettings() { OctaveCliPath = @"D:\GNU Octave\Octave-9.4.0\mingw64\bin\octave-cli.exe" };
 using (var octave = new OctaveContext())
 {
                    string funcDef = @" wt=[0.123456 1.234567 0.345678];  ...
    i = 1; ...
    outputs = {}; ...
    predict = zeros(1, 3); ...
    for k = 1:length(wt) ...
        outputs{i, k} = round(wt(k)); ...
        predict(i, k) = round(wt(k)); ...
    end ...
  
";
                    octave.Execute(funcDef);

                    var r1 = octave.Execute("disp(cell2mat(outputs))");
                    var r2 = octave.Execute("disp(predict)");

                    var result1 = r1.AsMatrix();
                    var result2 = r2.AsVector();
 }

MATLAB Compiler

直接编译为dll或者exe,需要依赖MCR(MATLAB Compiler Runtime)且调用dll之前要启动一个ngine 之类的东西。影响效率

.NET Assembly

打包 MATLAB函数

MATLAB中选APP菜单 找到库编译器 Library Compiler

  1. Type:选择目标类型 (这里选.NET Assembly

  2. Exported Functions:添加需要打包的函数文件

  3. Library information:重命名库名称,重命名类名称,或者添加类,分配函数所属类

  4. Package:打包

C#调用

打包好的dllfor_redistribution_files_only目录下,里面两个dll都可以使用

除了需要引用打包好的dll,还需要引用 MWArray.dll该文件在Matlab安装目录中,参考路径: 安装路径\MATLAB\R2023a\toolbox\dotnetbuilder\bin\win64\v4.0\

直接实例打包时设置的类名即可:

//添加引用
using System;
using TESTNative;
using MathWorks.MATLAB.NET.Arrays; 

//触发代码
private void TEST_Click(object sender, EventArgs e)
        {
            int[,] list = { { 1 }, { 2 }, { 3 }, { 4 } }; //列向量
            MWArray array = new MWNumericArray(list); //转换list格式

            TESTNative.Cal ts = new Cal();//定义目标类
            object resultObj = ts.TEST(1, array);// 1表示返回的结果数量,要小于等于Matlab对应函数实际的返回值数量
            //转换返回值
            object[] resultObjs = (object[])resultObj;
            double[,] calcResult = (double[,])resultObjs[0];
        }

参考

https://blog.csdn.net/qq_45389511/article/details/137199865


眼睛记得的光影,心记得的温度,它们不会消散,只是藏进岁月的褶皱里。某一天,风一吹,它们又鲜活如初...

Tim

infj 提倡者

站长

具有版权性

请您在转载、复制时注明本文 作者、链接及内容来源信息。 若涉及转载第三方内容,还需一同注明。

具有时效性

目录

欢迎来到Tim的博客,为您导航全站动态

45 文章数
4 分类数
3 评论数
48标签数

热门文章

D&F - Frida

2024-08-04

1716
D&F开服

2024-07-27

761
D&F - DP插件

2024-08-04

355

访问统计