matlab和C/C++混合编程--Mex

2023-11-19

 最近的项目需要matlab和C的混合编程,经过一番努力终于完成了项目要解决的问题。现在就将Mex的一些经验总结一下,当然只是刚刚开始,以后随着学习的深入继续添加。首先讲讲写Mex的一些常规规定,然后我们会重点关注混合编程中最难解决数据的问题--结构到底如何转换,并且后面会重点说一下自己的程序。

一、Mex的结构

先看一个简单的程序(该程序保存在matlab主目录下名字是mexDemon.cpp,或者在主目录下新建一个.cpp文件):

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
#include "mex.h" 
//加入头文件,该头文件在VS2010中无法include,但是不影响其在matlab中的编译,反而在matlab编译还需要include它
#include <vector>
using  namespace  std;
 
void  mexFunction( int  nlhs, mxArray *plhs[], int  nrhs, const  mxArray *prhs[])
//mexFunction就类似于main函数
{
     //nlhs代表的是输出参数的个数
     //plhs是一个指针数组,里面的指针指向mxArray类型,每一个指针指向一个输出
     //nrhs代表的是输入参数的个数
     //prhs是一个指针数组,里面的指针指向mxArray类型,每一个指针指向一个输入
 
  vector<vector< double > > array2d;
     double  *z;
     plhs[0] = mxCreateDoubleMatrix( 5, 6, mxREAL); //第一个输出是一个5*6的矩阵
     z = mxGetPr(plhs[0]); //获得矩阵的第一个元素的指针
     array2d.resize(5);
     int  ii = 0;
     for ( int  i = 0; i < 5; i++){
         for ( int  j = 0; j < 6; j++){
             z[i*6 + j] = ii;  //指针访问矩阵是列优先的,请自己循环程序和分析输出结果
             ii++;
         }
     }
 
/*
  *ans =
 
      0     5    10    15    20    25
      1     6    11    16    21    26
      2     7    12    17    22    27
      3     8    13    18    23    28
      4     9    14    19    24    29
  */

然后对Matlab编译应用程序mex的编译器进行设置,在命令窗口输入 Mex –setup。 然后跟着步骤走选择合适的编译器即可。

设置完编译器之后在命令窗口输入Mex mexDemon.cpp 进行编译生成.mexw64文件,生成之后便可以直接调用了,例如本例子可以这样调用,就是直接在命令窗口输入 a = mexDemon(); 返回值如上。


 二、C和Matlab的数据结构的转换

(1)数值的传递

matlab -> c++

1
x = mxGetScalar(prhs[0]); //该函数获取matlab传递过来的数值;

 c++ -> matlab

plhs[0] = mxCreateDoubleMatrix(1,1,mxREAL);//创建返回的矩阵,范围plhs[0]为mxArray类型
y = mxGetPr(plhs[0]);//获取返回plhs[0]的数据地址,其后可以修改y的值就可以返回了

一个实例(numDemon.cpp):

1
2
3
4
5
6
7
8
9
10
11
#include "mex.h"
 
void  mexFunction( int  nlhs, mxArray *plhs[],  int  nrhs,  const  mxArray *prhs[]){
     int  x = mxGetScalar(prhs[0]);  //将第一个输入参数转为Scalar标量,也就是单数值
     printf ( "%d\n" , x);  //打印
     
     double  *y;
     plhs[0] = mxCreateDoubleMatrix(1,1,mxREAL);  //让第一个输出参数指向一个1*1的矩阵
     y = mxGetPr(plhs[0]);  //获得矩阵的第一个元素的指针
     *y = 10;  //将其赋值为10
}

 如下图在命令窗口编译:


 (2)矩阵的传入与传出

关于传出(c++到Matlab, 就是第一个例子),下面可以再给一个例子是如何从matlab传入到c++,看下面这段代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
#include "mex.h"
 
void  mexFunction( int  nlhs, mxArray *plhs[],  int  nrhs,  const  mxArray *prhs[]){
     double  *dataCursor;
     vector<vector< double > > parms;
 
     dataCursor = mxGetPr(prhs[0]);  //得到输入矩阵的第一个元素的指针
     int  mrows = mxGetM(prhs[0]);    //获得矩阵的行
     int  ncols = mxGetN(prhs[0]);    //获得矩阵的列
     printf ( "%d_%d\n" , mrows, ncols);   //打印行和列
     
     parms.resize(mrows);   //初始化
     for ( int  i = 0; i < mrows; i++){
         parms[i].resize(ncols);
     }
 
     for ( int  i = 0; i < mrows; i++){
         for ( int  j = 0; j < ncols; j++){
             parms[i][j] = dataCursor[j * mrows + i];  //拷贝矩阵的元素到vector of vector
         }
     }
 
}

 同样在命令窗口编译即可。

 


(3)字符串的传入与传出

matlab -> c++ (传入)

1
2
char  *input_buf;
input_buf = mxArrayToString(prhs[0]); //使用mxArrayToString将mxArray转换为c、c++字符串

 c++ -> matlab (传出)

1
2
3
4
5
char  *output_buf; //定义字符串缓存
size_t  buflen = (mxGetM(prhs[0]) * mxGetN(prhs[0])) + 1; //获取字符串长度,mxGetM获取行数,mxGetN获取列数
output_buf=mxCalloc(buflen,  sizeof ( char )); //使用mxCalloc分配输出字符串数组
plhs[0] = mxCreateString(output_buf); //使用mxCreateString创建mxArray输出
mxfree(output_buf);

 一个实例(strDemon.cpp)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
#include "mex.h"
void  revord( char  *input_buf,  size_t  buflen,  char  *output_buf)
{
   mwSize i;
   if  (buflen == 0)  return ;
  
   for (i=0;i<buflen-1;i++)
     *(output_buf+i) = *(input_buf+buflen-i-2);
}
 
void  mexFunction(  int  nlhs, mxArray *plhs[],
                   int  nrhs,  const  mxArray *prhs[])
{
     char  *input_buf, *output_buf;
     size_t  buflen;
    
     buflen = (mxGetM(prhs[0]) * mxGetN(prhs[0])) + 1;  //因为本程序是翻转字符串,所以输入输出字符串的长度应该一样
    
     output_buf=mxCalloc(buflen,  sizeof ( char ));  //申请空间
    
     input_buf = mxArrayToString(prhs[0]);  //获得输入字符串
    
     revord(input_buf, buflen, output_buf);  //翻转字符串
    
     plhs[0] = mxCreateString(output_buf);
     mxFree(input_buf);
     return ;
}

同样编译一下即可。 

 


(4)cell的传入

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
#include "mex.h"
 
void  mexFunction( int  nlhs, mxArray *plhs[],  int  nrhs,  const  mxArray *prhs[]){
     mwSize cellNdim = mxGetNumberOfDimensions(prhs[0]);  //这里介绍两个函数mxGetNumberOfDimensions和mxGetDimensions
     const  int  *cellColPtr = mxGetDimensions(prhs[0]);
     //mxGetDimensions: 就是返回一个指针ptr,每一个指针所指向的值是每一个维度的元素个数。例如有矩阵3*2的矩阵,那么*(ptr)为3,*(ptr+1)为2.
     //mxGetNumberOfDimensions: 返回mxArray的维度。
     int  cellNRow = *(label_dims);
     int  cellNCol = *(label_dims + 1);
 
     mxArray *ptr;
     ptr = mxGetCell(prhs[0], 0);  //获取cell的第0个元素,返回一个mxArray指针,第二个参数代表cell中元素的下标
 
     mxArray *cellOfCell;
     cellOfCell = mxGetCell(ptr, 0);     //当然cell里面可以还是cell,那么应该再样写
 
     mxArray *cellOfStr;
     char  *chTmp;
     cellOfStr = mxGetCell(prhs[0], 0);  //当然cell里面可以是字符串
     chTmp = mxArrayToString(cellOfStr);
     printf ( "%s\n" , chTmp);
}

 后面待补充结构体和cell数组的传出,暂时还没遇到这样的需求。再贴上几个参考网址:

1.http://blog.sina.com.cn/s/blog_9db9f81901013yv2.html

2.http://blog.sina.com.cn/s/blog_80202a090100uhup.html

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

matlab和C/C++混合编程--Mex 的相关文章

  • 【笔记】下单但未支付的订单倒计时自动取消逻辑实现

    平常我们都用过淘宝 京东这些电商平台 同时肯定也在这些平台上面下过单 这种情况不保证大家都有遇到过 但做开发的 肯定也知道有这个环节的存在 确认货品配置无误之后 我们都会点击购买 随之而来的就是一个结算页 让你确认商品信息 收货地址 价格等
  • ElementUi的el-tree组件样式修改

    ElementUi的el tree组件样式修改 需求如下 下拉图标的修改 element ui中的原本的基本样式是这样的 所以第一步呢 就是要把这个下拉按钮的样式修改成加号 在vue文件中 修改样式即可 vue的项目在写样式的时候 回家上s
  • join表连接的三种算法思想:Nested-Loop Join和Index Nested-Loop Join和Block Nested-Loop Join和BKA

    一 Nested Loop Join 在Mysql中 使用Nested Loop Join的算法思想去优化join Nested Loop Join翻译成中文则是 嵌套循环连接 举个例子 select from t1 inner join
  • ChatGPT能为留学生做什么?错误使用有何后果?

    随着AI人工智能行业的迅速发展 越来越多的学生开始利用ChatGPT等软件来获得更高效便利的论文和作业辅助 然而 我们需要认识到一个严肃的问题 学生是否过度依赖AI助手来完成毕业论文 近期出现的Turnitin AI Detector是一个
  • 在Windows下使用vs2019编译libjpeg库

    一 库的编译 1 下载 libjpeg 源码 这里我下载的是 jpegsr9e zip 2 解压源码 3 进入解压后的目录 找到 makefile vs 文件 用文本编辑器打开并编辑 找到 语句 include
  • 设备管理过程

    复杂度2 5 机密度2 5 最后更新2021 04 19 AIX中对设备会有如下五个操作 define aix下能看到设备的定义 但驱动程序并没有加载或初始化 该设备不可用 lsdev看到设备时defined 很多逻辑设备 vg lv等 只
  • CTF练题(5)word隐写基础题,jpg图片隐写,敲击码解密

    2022 11 2 两道misc题目 题目一 word隐写基础 题目信息如下 以及一个无法打开的word文档 解题步骤 1 将该word文档拖入010Editor中进行分析 发现文件头显示为PK 压缩文件 将该文档后缀改为 zip 保存到桌
  • go-zero使用Etcd进行服务注册代码分析

    代码分析 github com tal tech go zero v1 2 3 core discov publisher go package discov import github com tal tech go zero core
  • ld链接器的--start-group和--end-group参数说明

    start group archives end group The archives should be a list of archive files They may be either explicit file names or
  • OpenLayers与Bootstrap样式冲突的解决

    在引入Bootstrap响应式布局样式后 OpenLayers图层瓦片会显示异常 在页面中加入以下样式可以解决 参见 http openlayers org dev examples bootstrap html
  • linux网络95值工具,Linux下网络故障排查工具之ping

    服务器运维人员在日常运维服务器的过程中经常会遇到服务器网络故障 有服务器硬件造成的 也有服务商网络问题造成的 也有区域网络问题造成的 这个时候就需要用到ping traceroute mtr这三个命令 1 ping 最简单的网络请求反馈命令
  • 粒子群算法优化的最小二乘支持向量机分类代码

    粒子群算法优化的最小二乘支持向量机分类代码 在数据挖掘和机器学习领域中 分类是一个非常基础而重要的问题 其中最小二乘支持向量机 LSSVM 是一种有效的分类方法 经常被应用于实际问题中 而粒子群算法 PSO 是一种优化算法 也可以用来优化L
  • C++之函数模板

    1 什么是模板 模板有什么作用 模板分为函数模板和类模板 函数模板是对函数功能框架的描述 具体功能由实际传递的参数决定 有了函数模板 编译器就会根据模板自动生成多个函数名相同 参数列表不同的函数 不需要手动写 例 求一个矩形面积 当传入的长
  • Tensorflow之Estimator(二)实践

    1 前言 这篇文章介绍Tensorflow的高级API 模型的建立和简化过程 2 Estimator优势 本文档介绍了Estimator一种可极大地简化机器学习编程的高阶TensorFlow API 用了Estimator你会得到数不清的好
  • 一些JDK自带的性能分析利器

    有时候碰到服务器CPU飙升或者程序卡死之类的问题 一般都不太好定位 这类bug一般都隐藏的比较深并且还可能是偶发性的 比较棘手 对于此类问题 一般我们都有固定的分析流程 借助于JDK自带的一些分析工具 比如jstack jmap jstat
  • 超全汇总,性能测试常用指标大全(重要)

    目录 导读 前言 一 Python编程入门到精通 二 接口自动化项目实战 三 Web自动化项目实战 四 App自动化项目实战 五 一线大厂简历 六 测试开发DevOps体系 七 常用自动化测试工具 八 JMeter性能测试 九 总结 尾部小
  • 三相桥式全控整流电路仿真--(Matlab仿真2)

    仿真环境 Matlab 2018a 使用模块 1 Three Phase V I Measurement1 2 Multimeter 3 Universal Bridge 4 Selector 5 Mean 测量平均电压 6 Pulse G
  • pycharm如何连接数据库并往数据库插入内容

    1 创建connection对象 2 创建cursor对象 游标对象 主要用于操作数据库 3 执行查询 4 关闭cursor对象 5 关闭connection 首先要先安装pumysql库 pip install pymysql 连接测试
  • 微服务应用大行其道,我提供一个dto和entity转换工具类,方便大家做转换,少写机械代码,多陪陪家人...

    微服务应用大行其道 我提供一个dto和entity转换工具类 方便大家做转换 少写机械代码 多陪陪家人 该工具类主要是对dozer进行了封装 使用过程代码量极少 废话少说 贴代码了 import java util ArrayList im
  • 使用vscode编辑和提交github仓库代码

    写在前面 在github上想删除仓库中的某个文件或文件夹 亦或是重命名操作都很麻烦 这里提供一种vscode的解决方案 在vscode中克隆远程github仓库 然后对代码或文件进行编辑 最后提交即可 就和管理本地文件一样方便 准备工作 下

随机推荐

  • react.js的介绍

    关于React React部分的内容包含了所有授课的思路 React的起源和发展 React 起源于 Facebook 的内部项目 因为该公司对市场上所有 JavaScript MVC 框架 都不满意 就决定自己写一套 用来架设Instag
  • 计算机网络之数据链路层协议总结

    数据链路层 1 数据链路层介绍 2 ARP协议 2 1 ARP的工作流程 2 2 ARP数据报格式 3 NAT技术 3 1 NAT转换过程 3 2 NAPT技术 动态NAT重载 4 DNS技术 4 1 域名层级关系 4 2 域名解析流程 5
  • 程序员如何认识自己? 怎么知道自己适合做什么?人生路上的困惑 应不应该转行

    这个问题其实从毕业工作后就开始思考了 到底什么才是自己适合的工作 怎么才能从自己的工作当中找到兴趣 有朋友吐槽不喜欢现在的生活 不喜欢现在的工作 感觉不合适 如果被吐槽之后 我真的是按照套路去回答 嗯 我理解你 你现在肯定因为自己的生活和工
  • 自定义view之无限滚动的刻度尺

    具体思路是把一个view分成三段 当总长度 gt 40个刻度向左滚动 滚动到2 3的时候view移动到1 3出然后刷新显示的刻度这时为第一页 一次更新页数 当向右滚动的时候滚动且不为第一页则每滚动到1 3处view移动到2 3处 之后在添加
  • 第1090期AI100_机器学习日报(2017-09-12)

    AI100 机器学习日报 2017 09 12 神经网络机器翻译 NMT 实践笔记 爱可可 爱生活 如何在Chatbot中应用深度学习 ChatbotsChina 论文推荐 像CNN一样快速训练RNN 机器之心Synced 基于Libsvm
  • Django2 Postman 模拟POST提交,提示:Forbidden (CSRF cookie not set.) 403

    解决方法 去除django项目中settings py中的 MIDDLEWARE 的 django middleware csrf CsrfViewMiddleware 既可
  • QT的信号与槽原理(经典)

    QT的信号与槽原理 经典 信号与 槽作为 QT的核心机制在 QT编程中有着广泛的应用 本文介绍了信号与 槽的一些基本概念 元对象工具以及在实际使用过程中应注意的一些问题 QT是一个跨平台的C GUI应用构架 它提供了丰富的窗口部件集 具有面
  • .faust勒索病毒数据怎么处理

    引言 近年来 随着科技的迅猛发展 网络安全问题愈发突出 特别是勒索病毒的威胁日益严峻 其中 Faust勒索病毒作为一种新型的恶意软件 引起了全球范围内的广泛关注和担忧 本文91数据恢复将对Faust勒索病毒进行深入分析 探讨其传播方式 危害
  • 利用Python制作本地Excel的查询与生成的程序

    前言 大家好 今天教大家利用Python制作本地Excel的查询与生成的程序 需求 制作一个程序 有一个简单的查询入口 实现Excel的查询与生成 实验步骤 1打开一个exe 弹出一个界面 2有一个查询 卡号 点击查询 3下方展示查询的结果
  • 何谓离散制造

    离散制造 Intermittent Discrete Manufacturing 产品的生产过程通常被分解成很多加工任务来完成 每项任务仅要求企业的一小部分能力和资源 企业一般将功能类似的设备按照空间和行政管理建成一些生产组织 部门 工段或
  • plasma桌面特效无效的解决办法

    前段时间重装了Arch Linux 用了好看的Plasma桌面 但是最近这几天桌面特效突然没有了 让我非常郁闷 于是乎我开始动手排查起来 由于前几天折腾显卡驱动 最后还是没折腾成功 所以我一开始将问题定位到显卡驱动上 然后谷歌了各个显卡驱动
  • Mysql锁机制详解

    Mysql锁 在多线程当中如果想保证数据的准确性是如何实现的呢 没错 通过同步实现 同步就相当于是加锁 加了锁以后有什么好处呢 当一个线程真正在操作数据的时候 其他线程只能等待 当一个线程执行完毕后 释放锁 其他线程才能进行操作 那么我们的
  • 在Ubuntu上编写一个开机自启动的Python脚本

    注意事项 如果脚本没有执行 首先应该考虑执行权限问题 查看脚本和相应的文件是否有执行权限 如果没有需要赋予执行权限 方法1 1 编写一个shell脚本文件 例如python auto sh 文件内容 2 编写start py文件 里面执行你
  • wps二维码根据一列自动生成_公文智能写作小程序上线了!一键生成公文!而且完全免费!...

    01 免费的公文写作AI 看过 秘书工作手记2 怎样写出好公文 的筒子们或许有察觉 石头对一切 投机取巧 的写材料方式 都抱有浓厚的兴趣 一切公文写作领域的工具创新 都会刺激我敏感的神经 比如 搜索引擎 资料库是我们写材料的常用工具 但这工
  • 金蝶kis专业版系统登录服务器,金蝶kis专业版怎么远程连接服务器

    金蝶kis专业版怎么远程连接服务器 内容精选 换一换 您可以借助报表服务制作各种各样的报表 无论是简单的还是复杂的报表 同时系统提供订阅功能方便用户对报表进行订阅 本文主要介绍RDS使用SSRS Reporting Services 报表服
  • 学习python第一天

    汉诺塔递归问题 python默认参数问题 参数一开始可以给一个默认值 如果想让一个函数能接受任意个参数 我们就可以定义一个可变参数 def fn args print args 可变参数的名字前面有个 号 我们可以传入0个 1个或多个参数给
  • gpuz怎么看显存颗粒

    gpuz可以帮助一些用户查看电脑的一切显卡参数 对于想要了解显卡的网友来说使用起来是非常方便的 不过有些网友是刚开始使用 还不知道gpuz怎么看显存颗粒 下面小编就教下大家gpuz查看显存颗粒的方法 首先 显存颗粒是显存的物理存储组成单元
  • 单独捕获dubbo异常

    一 定义一个rpc异常去继承自己自定义捕获的异常 public class RpcRuntimeException extends BadRequestException implements Serializable public Rpc
  • 用vite命令搭个react移动端项目,实现canvas碰撞效果(按需导入antd-mobile,pxtorem适配)

    前言 最近看见大家都在卷react源码 突然就心慌了 但是自己的操作水平还有待提高 现在看源码也需要循序渐进的 打算还是从写代码慢慢理解功能再去看源码 所以就尝试使用vite这个构建工具进行尝试构建一个react项目 因为是第一次使用 也是
  • matlab和C/C++混合编程--Mex

    最近的项目需要matlab和C的混合编程 经过一番努力终于完成了项目要解决的问题 现在就将Mex的一些经验总结一下 当然只是刚刚开始 以后随着学习的深入继续添加 首先讲讲写Mex的一些常规规定 然后我们会重点关注混合编程中最难解决数据的问题