QQ登录

只需要一步,快速开始

 注册地址  找回密码
查看: 4408|回复: 10
打印 上一主题 下一主题

[课件资源] Matlab调用c程序

[复制链接]
字体大小: 正常 放大
梦溪517        

18

主题

5

听众

230

积分

升级  65%

  • TA的每日心情
    开心
    2014-2-12 10:47
  • 签到天数: 52 天

    [LV.5]常住居民I

    群组Matlab讨论组

    群组C 语言讨论组

    群组学术交流B

    群组学术交流A

    群组2013年数学建模国赛备

    跳转到指定楼层
    1#
    发表于 2012-8-28 20:47 |只看该作者 |倒序浏览
    |招呼Ta 关注Ta

    & S5 I) b' c1 Z; K9 t7 OMatlab调用c程序8 ]" p& P* p% c. Y/ `
    文章来源:不详 作者:佚名 2 Q! p2 j9 t6 f4 Q  `; f+ y% W: `( p

    $ F, J+ L: {  X$ _2 Y--------------------------------------------------------------------------------
    1 ^! F& j5 o. ?$ ?/ L1 o. ?* b/ b* S: v0 p- ?! M+ d0 |  i0 b2 F
    该文章讲述了Matlab调用c程序.3 ^% W4 K( `7 F0 f6 A; B+ M2 x

    : G4 d# P4 P. u, u6 h! {  y方法:
    ; t1 P9 F- o* A) w8 ~$ I0 i- J第一步:要先在matlab中安装c程序编译器,步骤如下:
    4 Q" P% X: C! ~0 q( L$ u! i. e9 t键入命令:mex -setup
    & R. H* W/ A. q0 d+ |选择c/c++编译器;. l5 n% f( k' n, }+ z; v. _: k
    选择c/c++编译器版本;% _, e. h" d6 L2 B1 G7 ~! f/ L
    确认。
    # R2 v6 t, ], H9 q; A0 S" L第二步:键入:mex *.c+ n$ z9 i2 z1 K, O5 x0 e7 U7 Z9 h

    " ~9 Z' h+ L7 o; F" ]3 R*********************************************************************************************************************************************, U1 P( O- e6 E/ A/ h
    # ~6 K6 Y; n& L  L8 r' v# N
    实例介绍:【转】
    9 x' F. h- `! z+ |' k% |# F
    ( C( A9 C0 D1 S( B' c如果我有一个用C语言写的函数,实现了一个功能,如一个简单的函数:3 E# W+ o* o' O5 g7 f% a
    double add(double x, double y) {2 u+ }! S: g. `' z
     return x + y;# [/ k, G3 F( c8 g3 p
    }
    . ~) a) a5 q5 _, H现在我想要在Matlab中使用它,比如输入:0 g1 N( C3 }6 L
    >> a = add(1.1, 2.2)& m0 d6 J$ P, [7 H$ O, [
    3.30009 B5 q$ J4 l( c% C
    要得出以上的结果,那应该怎样做呢?, N% ]+ _- X' g  Q0 Y! o
    解决方法之一是要通过使用MEX文件,MEX文件使得调用C函数和调用Matlab的内置函数一样方便。MEX文件是由原C代码加上MEX文件专用的接口函数后编译而成的。* M4 E: _$ K8 O6 f, }; W/ |8 w' ^
    可以这样理解,MEX文件实现了一种接口,它把在Matlab中调用函数时输入的自变量通过特定的接口调入了C函数,得出的结果再通过该接口调回Matlab。该特定接口的操作,包含在mexFunction这个函数中,由使用者具体设定。
    & q, U# d! X( U! X所以现在我们要写一个包含addmexFunctionC文件,Matlab调用函数,把函数中的自变量(如上例中的1.12.2)传给mexFunction的一个参数,mexFunction把该值传给add,把得出的结果传回给mexFunction的另一个参数,Matlab通过该参数来给出在Matlab语句中调用函数时的输出值(如上例中的a)。; j/ n8 J  [% z! G0 K  S
    比如该C文件已写好,名为add.c。那么在Matlab中,输入:$ W( O) r0 F% [
    >> mex add.c
    1 ?3 ?2 L  y) E. f就能把add.c编译为MEX文件(编译器的设置使用指令mex -setup),在Windows中,MEX文件类型为mexw32,即现在我们得出add.mexw32文件。现在,我们就可以像调用M函数那样调用MEX文件,如上面说到的例子。所以,通过MEX文件,使用C函数就和使用M函数是一样的了。
    % o& I+ o* d( O+ \, @我们现在来说mexFunction怎样写。
    $ W! ~: O3 G4 gmexFunction的定义为:
    4 c% q' ?$ N, H& ^) Q$ m' s# {2 x  uvoid mexFunction(
    - `5 `! c: W! i     int nlhs,
    , }% m: f1 m( `     mxArray *plhs[],/ g1 o- c5 r" v* s( |4 X
         int nrhs,) y! N* `1 \: o3 V) r: w1 l
         const mxArray *prhs[]) {0 D- h7 V2 J0 V
    / ^- Y% ]- }2 O0 z- }/ _: @
    }
      ~) O; D. ?; b  }2 i8 ?3 E! C可以看到,mexFunction是没返回值的,它不是通过返回值把结果传回Matlab的,而是通过对参数plhs的赋值。mexFunction的四个参数皆是说明Matlab调用MEX文件时的具体信息,如这样调用函数时:
    4 v: V0 W5 t+ O8 H0 A6 x- Z! p# b>> b = 1.1; c = 2.2;
    " @0 S4 ~$ X7 T" u% X& e1 H>> a = add(b, c)
    + B# T& X. i' hmexFunction四个参数的意思为:) o6 m7 `" x0 d. V5 K9 ?
    nlhs = 1,说明调用语句左手面(lhsleft hand side)有一个变量,即a
    # B5 j+ x; y5 R/ Q+ u" C. r0 z+ unrhs = 2,说明调用语句右手面(rhsright hand side)有两个自变量,即bc+ V! R+ {5 |3 {" q, p8 X
    plhs是一个数组,其内容为指针,该指针指向数据类型mxArray。因为现在左手面只有一个变量,即该数组只有一个指针,plhs[0]指向的结果会赋值给a
    8 u5 p# T* t- `prhsplhs类似,因为右手面有两个自变量,即该数组有两个指针,prhs[0]指向了bprhs[1]指向了c。要注意prhsconst的指针数组,即不能改变其指向内容。
    ( k$ h9 T% r% N" @* q因为Matlab最基本的单元为array,无论是什么类型也好,如有double arraycell arraystruct array……所以a,b,c都是arrayb = 1.1便是一个1x1double array。而在C语言中,Matlabarray使用mxArray类型来表示。所以就不难明白为什么plhsprhs都是指向mxArray类型的指针数组。. I' P9 M6 d; ^. M2 q* z3 E
    完整的add.c如下:
    2 V7 C/ P' K* N// add.c0 n. G4 r' j1 U4 J
    #include "mex.h" // 使用MEX文件必须包含的头文件 // 执行具体工作的C函数2 C# p8 t8 x, ~" y6 H2 p
    double add(double x, double y) {
    $ S$ {7 m& j! ^ return x + y;
    & r, G/ h5 W3 ~3 h} // MEX文件接口函数* O6 @7 C. _' a0 o- I
    void mexFunction(
    # `. k. y% o0 ^# D$ j5 o# h int nlhs,
    ; ]& [; `' w% U: g- N3 s mxArray *plhs[],
    $ m' q8 p5 K3 }6 N& m: M. K int nrhs,1 w' I4 M$ \* \! S2 U+ Q/ h
     const mxArray *prhs[]) {
    / K" X  Y4 X+ e" t" J6 h# i7 j: O double *a;
    : I, n: F( y3 t! O7 @+ O' O7 N3 Z+ _7 D double b, c;. {" |$ O& O: ]$ z3 |+ l
     plhs[0] = mxCreateDoubleMatrix(1, 1, mxREAL);; u" L) S; g$ {! w# D+ B2 E% Z
     a = mxGetPr(plhs[0]);# D! o1 p' S3 I( e6 K, l8 c2 A) M) R
     b = *(mxGetPr(prhs[0]));3 D' q  Y/ r  G8 U  F( Q1 B& L
     c = *(mxGetPr(prhs[1]));
    8 D( c3 M, n' E5 H *a = add(b, c);& M$ `( _9 v+ H. j5 A! C
    }
    4 P/ M, s- f" b  @  P! ^# z" RmexFunction的内容是什么意思呢?我们知道,如果这样调用函数时:4 v; k0 S: j2 y, Y+ C* R. E5 s
    >> output = add(1.1, 2.2);
    % f) f# ]. s7 T& ^6 v  k在未涉及具体的计算时,output的值是未知的,是未赋值的。所以在具体的程序中,我们建立一个1x1的实double矩阵(使用mxCreateDoubleMatrix函数,其返回指向刚建立的mxArray的指针),然后令plhs[0]指向它。接着令指针a指向plhs[0]所指向的mxArray的第一个元素(使用mxGetPr函数,返回指向mxArray的首元素的指针)。同样地,我们把prhs[0]prhs[1]所指向的元素(即1.12.2)取出来赋给bc。于是我们可以把bc作自变量传给函数add,得出给果赋给指针a所指向的mxArray中的元素。因为a是指向plhs[0]所指向的mxArray的元素,所以最后作输出时,plhs[0]所指向的mxArray赋值给output,则output便是已计算好的结果了。/ I# V5 i% `$ A( R, n
    上面说的一大堆指向这指向那,什么mxArray,初学者肯定都会被弄到头晕眼花了。很抱歉,要搞清楚这些乱糟糟的关系,只有多看多练。9 L! X( ]1 ^1 u8 e9 }7 a. T
    实际上mexFunction是没有这么简单的,我们要对用户的输入自变量的个数和类型进行测试,以确保
    * R( T  |# ^; ^- L' X输入正确。如在add函数的例子中,用户输入char array便是一种错误了。
    - ]3 r5 e' ]4 T9 }+ K从上面的讲述中我们总结出,MEX文件实现了一种接口,把C语言中的计算结果适当地返回给Matlab罢了。当我们已经有用C编写的大型程序时,大可不必在Matlab里重写,只写个接口,做成MEX文件就成了。另外,在Matlab程序中的部份计算瓶颈(如循环),可通过MEX文件用C语言实现,以提高计算速度。7 Z9 c% U0 q1 J
    * g4 v, J, v# Y7 D
    *********************************************************************************************************************************************
    5 c+ w3 p! F7 R. C5 h0 e) I7 w5 q% l/ F& c3 E
    mex 的目的,( Z0 |3 K9 c# d

    # n8 E2 {/ c, I. d7 R' u! {通过C/C++语言编写代码,Matlab中将其编译成mex文件主要可以做以下几方面的事情:/ ^9 @' Y+ A, ~: u. X' o

    7 D" j! T7 h# E  W- f/ ]1、加快程序的执行速度. Matlabfor上如老牛拉车的速度确实让人抓狂.
    ; e; U9 l2 X3 S: l8 t- d7 [# c
      x  g* k; K3 n9 x+ O5 W2、将Matlab作为C++的开发调试环境.尤其是有大量数据需要处理时,Matlab观察其中间结果十分方便.
    " D' @: G6 F# w5 }  r' f& G0 S. k- G$ c6 G7 t4 y9 @
    3、据称可以弥补Matlab硬件设备接口的薄弱环节.
    ( L; v4 W/ u" b# q9 I# \. E2 O: Y6 K! I8 E- `
    今天写了第一个使用MEX.
    1 M. s7 X, ^. a  G; ~
    2 F2 o! f* d0 c" N/ F" Z+ w$ `+ `- [一个简单的对Matlab普通数值矩阵的操作.
    , c& ]% I, Z* U. o; \9 B/ A* h4 a/ f& w$ ~( M! X" W) ]
    其中Matlab规定的与操作系统版本有关的mwSize,mwIndex, size_t32位系统上其实本质上就是int,所以
    - l& [, s0 P& [: n$ S6 q2 m* J+ N8 ~9 v! G
    一律用int代替.6 |3 r* a* U/ Y" e
    2 f7 Q* i/ ?! @2 n5 g
    #include "mex.h"
    7 F% N4 X/ H0 Q#include <iostream>, T* N: T6 F3 ~/ x! P! g
    / o% H) K" L* p4 {
    void mexFunction(int nlhs,mxArray *plhs[],int nrhs,const mxArray *prhs[])
    ! ?- [5 E; }' G: M8 n{
    6 U2 T& ~* `$ ~7 i& t4 p4 N- j1 X( N1 _
    int i,j,k;
    $ `$ {( Y$ T" zint index;
    - I4 B! g5 X' ?8 J' m  y: odouble* pr=NULL;  A, ?# x, S' L- G$ i  q
    double* pi=NULL;7 w2 P& L  J( W3 b
    int M,N;
    ) D' u9 m. {$ vint ndim;
    ! b- v' s# H3 g9 q8 V; Cint dims[2];
    4 L3 R$ P9 J% m* m* ifor (i=0;i<nrhs;i++)
    - t: k/ b- I0 S* m# T# o1 T{
    + ~& g# K0 v2 y& N) G2 y3 w   if ((mxIsDouble(prhs))&&(mxGetNumberOfDimensions(prhs)==2))
    " l8 N7 D$ ^! ?: U  \, A1 ~   {+ ]( _' O9 [! J& @
        pr=mxGetPr(prhs);. ~/ z! R* n6 z! l
        pi=mxGetPi(prhs);
    : C- i# {) j7 l- c5 Z* o    M=mxGetM(prhs);
    & q+ k; m0 Z; t3 x6 R    N=mxGetN(prhs);
    * ]4 B, [& F+ h7 a2 O. Q% ?    ndim=mxGetNumberOfDimensions(prhs);
    * m: b9 u$ f! G4 ~6 N: f) Z3 x" I; Z, a$ k  Y& v0 j
        mexPrintf("变量%d:\n",i);
    9 B0 C( ]9 N) J    for (j=0;j<M;j++)  ^) e, {$ }7 h) i! w
        {. m% T' @5 X/ d8 [* D
         dims[0]=j;
    , j/ ~6 P$ O+ c- U* l6 G     for (k=0;k<N;k++)5 K/ J- q5 m5 z
         {$ d4 y1 u  G. [( s$ s
          dims[1]=k;
    ' C6 }: Y/ I: i' i      index=mxCalcSingleSubscript(prhs,ndim,dims);6 `+ J- Q. O- o4 p: T! o
          if (pi==NULL)4 F0 p6 S  k' Y# y2 ?2 Y
          {
    ( `# u$ r% p) n/ b: h       mexPrintf("%6.2f",pr[index]);( S0 m8 y. n4 P  @1 x  E% d
          }
    & x5 Q& ^5 N# e, e      else{
    , r9 }, t! ~! i8 ]       mexPrintf("%6.2f+ %6.2fj",pr[index],pi[index]);
    3 V3 j. s2 M. e& L1 V" y' c      }2 [5 N2 [8 Z  R( O5 G
         }; }0 O; Z! g: r6 Q  w3 G: A5 H6 m1 n
         mexPrintf("\n");
    ! C# l  f' T8 b; K0 Q
    2 C" A! l8 h  T* x2 X    }3 }6 q5 O9 [* p* }; p
      
    9 X4 s# v0 z) W6 D- I: L   }
    . o1 k: X) {8 \   else{3 z* p$ x8 r- ]& I
        mexPrintf("input NUMB %d matrix is not 2 dims&double numerical array\n",i);
    / t  f* n# H/ k}) ?+ p6 x$ U8 B' T2 \- x; T
    & t, n) d. F7 ~

    5 \$ r& j" C' K6 U6 Q1 w}
    ! r0 w7 u# R& j- c+ P& @- v. c% D) x+ k( h, I! e! {' w. |& {' f
    }* R$ j7 M: S: c7 ?  E4 K
    % x5 s  U: S1 R* M6 O
    Result:6 U$ R# V2 N6 r9 o6 C% g, ~1 `( R8 A

    7 }0 G/ B2 s0 F/ A* ?: r/ Y>>mex test.cpp( u9 T; V2 x6 O* {
    >> test(a,b,c)$ u( [0 y5 |! O4 A& A- D4 x8 j) E) H
    变量0:4 }1 Q4 B$ e: T( d) T. R2 K
    0.35 0.62 0.83/ @3 i: r' F  U3 |( z. h% K
    0.20 0.47 0.59
    ) b& ^* r. d) h# b6 o0.25 0.35 0.55
    & Q4 S/ i; o5 f变量1:* A' C5 E& e( z
    0.92 0.38 0.53 0.57
    ' q+ w: [  k$ H$ l1 w% Z0.29 0.57 0.78 0.47
    9 D: J1 B# i3 t# r; R3 \6 k0.76 0.08 0.93 0.01& u* V- ]- e( U0 d4 A
    0.75 0.05 0.13 0.347 e& B) g* r$ e2 n
    变量2:
    , p3 e/ c, C. e  R8 `; ~0.16+   0.87j 0.60+   0.43j 0.45+   0.14j 0.83+   0.85j 0.11+   0.08j* P% l% i. X$ F! _$ V  K
    0.79+   0.08j 0.26+   0.91j 0.08+   0.87j 0.54+   0.62j 0.96+   0.24j
    % ?1 m3 U2 Q( X2 P( o0.31+   0.40j 0.65+   0.18j 0.23+   0.58j 1.00+   0.35j 0.00+   0.12j
    & ?" {$ V+ `8 y( H; g0.53+   0.26j 0.69+   0.26j 0.91+   0.55j 0.08+   0.51j 0.77+   0.18j
    " L6 D8 S% S/ R6 c3 E0.17+   0.80j 0.75+   0.15j 0.15+   0.14j 0.44+   0.40j 0.82+   0.24j
    ; |' p2 D% H' f: c+ r$ T>> help test% l) n  @% k  o1 _3 d* G4 |
    本程序用于调试mx______函数.5 u# @2 x+ _/ Y. Y8 N

    , J# C- O% V2 X- u
    $ }' P) X; u; x  E6 ?% |, N0 n' o本文来自: 高校自动化网(Www.zdh1909.com) 详细出处参考(转载请保留本链接)http://www.zdh1909.com/html/matlab/14744.html
    : d+ [' X6 t0 f1 s7 P' Z1 \1 E; r1 q6 P! B  N
    下面是其附件,内容一样,方便下载 Matlab调用c程序.doc (41.5 KB, 下载次数: 10)
    zan
    已有 1 人评分体力 收起 理由
    天海星云 + 5 很不错的,鼓励共享。

    总评分: 体力 + 5   查看全部评分

    转播转播0 分享淘帖0 分享分享0 收藏收藏0 支持支持0 反对反对0 微信微信

    32

    主题

    50

    听众

    2988

    积分

  • TA的每日心情
    慵懒
    2024-7-11 11:07
  • 签到天数: 543 天

    [LV.9]以坛为家II

    社区QQ达人 邮箱绑定达人 发帖功臣 新人进步奖 风雨历程奖 最具活力勋章

    群组小草的客厅

    群组数学建模认证项目实训

    群组我们一定会赢

    群组哈尔滨工业大学建模团

    群组聊天

    回复

    使用道具 举报

    0

    主题

    5

    听众

    101

    积分

    升级  0.5%

  • TA的每日心情
    开心
    2014-4-20 15:49
  • 签到天数: 4 天

    [LV.2]偶尔看看I

    群组Matlab讨论组

    群组2011年第一期数学建模

    群组LINGO

    回复

    使用道具 举报

    0

    主题

    7

    听众

    272

    积分

    升级  86%

  • TA的每日心情
    开心
    2014-9-22 15:14
  • 签到天数: 55 天

    [LV.5]常住居民I

    回复

    使用道具 举报

    tequila33        

    0

    主题

    6

    听众

    78

    积分

    升级  76.84%

  • TA的每日心情
    奋斗
    2013-2-4 10:21
  • 签到天数: 8 天

    [LV.3]偶尔看看II

    自我介绍
    想试试、、
    回复

    使用道具 举报

    lieove 实名认证       

    4

    主题

    7

    听众

    122

    积分

    升级  11%

  • TA的每日心情
    无聊
    2014-6-11 18:56
  • 签到天数: 23 天

    [LV.4]偶尔看看III

    群组Matlab讨论组

    群组数学建模

    群组数学建模保研联盟

    群组第四届数学中国美赛实

    回复

    使用道具 举报

    2

    主题

    8

    听众

    84

    积分

    升级  83.16%

  • TA的每日心情

    2013-2-16 14:17
  • 签到天数: 9 天

    [LV.3]偶尔看看II

    自我介绍
    数模
    回复

    使用道具 举报

    墨羽飞        

    0

    主题

    6

    听众

    480

    积分

    升级  60%

  • TA的每日心情
    奋斗
    2015-8-6 10:29
  • 签到天数: 143 天

    [LV.7]常住居民III

    社区QQ达人 邮箱绑定达人

    群组第四届cumcm国赛实训

    回复

    使用道具 举报

    fjnanyuan        

    4

    主题

    9

    听众

    130

    积分

    升级  15%

  • TA的每日心情

    2013-5-10 08:19
  • 签到天数: 30 天

    [LV.5]常住居民I

    自我介绍
    我不恨数模
    回复

    使用道具 举报

    2

    主题

    6

    听众

    117

    积分

    升级  8.5%

  • TA的每日心情
    开心
    2013-9-18 23:25
  • 签到天数: 53 天

    [LV.5]常住居民I

    群组Matlab讨论组

    群组2013认证赛A题讨论群组

    群组数学建模

    回复

    使用道具 举报

    您需要登录后才可以回帖 登录 | 注册地址

    qq
    收缩
    • 电话咨询

    • 04714969085
    fastpost

    关于我们| 联系我们| 诚征英才| 对外合作| 产品服务| QQ

    手机版|Archiver| |繁體中文 手机客户端  

    蒙公网安备 15010502000194号

    Powered by Discuz! X2.5   © 2001-2013 数学建模网-数学中国 ( 蒙ICP备14002410号-3 蒙BBS备-0002号 )     论坛法律顾问:王兆丰

    GMT+8, 2026-5-25 20:49 , Processed in 0.449703 second(s), 112 queries .

    回顶部