QQ登录

只需要一步,快速开始

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

Lu基于系统内置对象创建扩展数据类型,小矩阵乘效率测试

[复制链接]
字体大小: 正常 放大
forcal 实名认证       

45

主题

3

听众

282

积分

升级  91%

  • TA的每日心情
    难过
    2012-8-27 18:22
  • 签到天数: 1 天

    [LV.1]初来乍到

    跳转到指定楼层
    #
    发表于 2011-10-23 09:37 |只看该作者 |正序浏览
    |招呼Ta 关注Ta
        本例中,我们将基于系统内置实数数组创建矩阵(matrix)类型,即:基本类型为luDynData_realarray(标识实数数组),扩展类型为matrix(标识矩阵)。为了简单,我们仅处理二维实数数组即矩阵类型。3 V. i4 ^9 Q, e' `& J
    : a4 ?( y% k- Q$ m) L7 q( |
        基本要点:  m+ r% y9 s0 H$ Y& i: C  H8 F  U% X1 F

    4 ]5 H# D  H+ P2 E  T    (1)为扩展类型matrix编写运算符重载函数OpMatrix。
    6 j$ \" _. T5 e: F: c# U. E/ s
    ! ^+ t$ w5 Y8 _# c8 N: l/ o5 l9 r    (2)用函数LockKey将重载函数OpMatrix注册到Lu,锁定的键的类型即为matrix,要注册为常量,以便于使用。: o9 a, T+ O0 v
    " O' `4 u. r9 h4 m5 _7 m# h3 t  V
        (3)为扩展类型matrix编写其他操作函数(本例未提供)。+ @" u6 i2 Z3 o$ _( P6 H' O
    # p4 S/ L6 T' s2 [) [" _
        (4)用函数LockKey解锁键matrix(本例中,程序退出时会自动解锁,故可以不用)。
    1. #include <windows.h>' _3 C$ ?- A8 h. Q\\" W! Q$ `
    2. #include <iostream>
    3. 8 S6 T* ]2 `6 V. v
    4. #include <math.h>
    5. * K% ^4 G; B0 h1 o
    6. #include "lu32.h"
    7. $ J5 Z* O4 a' s1 G5 J6 Z

    8. - l; L( b' a9 U; x5 g$ t' k. W
    9. #pragma comment( lib, "lu32.lib" )5 E/ B3 d4 F7 w  P* t# X9 A9 m

    10. & k\\" ^9 W& O4 C6 w: \+ C# r7 ]0 Y
    11. using namespace std;# H3 _1 B: |# Y! Z# ~0 c
    12. 6 \% X8 m& D2 H: o
    13. luKEY Matrix=-1000;        //标识矩阵类型,最终的Matrix由LockKey决定: D- Z& |4 E6 A\\" g! M% ?, D2 q3 x

    14. + H- |# M( k6 C\\" h+ I, U
    15. void _stdcall LuMessage(wchar_t *pch)//输出动态库信息,该函数注册到Lu,由Lu二级函数调用   T# [4 V4 l\\" r6 H
    16. {
    17. 3 G( J4 |0 r2 K: C6 b
    18.         wcout<<pch;
    19. * a; h6 x+ e# [3 v) k# M
    20. }9 y  W1 v  E* V+ X: \
    21. void _stdcall DelMatrix(void *me)        //用于LockKey函数,因为是基于系统内置实数数组创建矩阵,故该函数什么也不做
    22. 6 P; ?8 J2 J3 }& ~' C# P
    23. {1 u+ p) Y# s0 Y( I
    24. }9 p6 E# }9 s1 l8 Y: i
    25. LuData _stdcall OpMatrix(luINT mm,LuData *xx,void *hFor,int theOperator)        //运算符重载函数,用于LockKey函数$ h$ l4 \& Z0 m2 w! }* ?, a
    26. {# m9 \; e& J8 D
    27.         LuData a;
    28. ! T* w3 C; H( W0 A; N
    29.         luRealArray *pRealArray1,*pRealArray2,*pRealArray3;
    30. 7 T1 h\\" s; |* ?3 p; M( ^- r
    31.         luVOID i,j,k,m,n,u,v;- Y+ X+ B! w# [, t& r0 _+ N2 ?8 E' A
    32.         double *pa,*pb,*pc;4 ?/ i( M  w* W( A/ b
    33.         luMessage pMessage;- n! g* C- K$ A4 f* w: |
    34.         wchar_t wchNum[32];2 D2 T& W8 r! a1 P8 U: ]: n' V
    35.         char chNum[32];
    36.   F; o# h6 F2 h  D5 l\\" B9 L- C5 b
    37.         a.BType=luStaData_nil; a.VType=luStaData_nil; a.x=0;
    38. 9 Z( a9 r) q* Y* p0 y
    39.         switch(theOperator)+ b! E( j- S  m6 Y) Y: U
    40.         {, D\\" M; ~4 O- D/ _/ ?; r/ k
    41.         case 2:        //重载运算符*
    42. * R9 Y8 F/ O5 k+ Q2 K' h/ }2 `\\" y6 x. D
    43.                 pRealArray1=(luRealArray *)SearchKey((char *)&(xx->x),sizeof(luVOID),luDynData_realarray);
    44. 5 |8 T4 X. K9 x* e  J4 y( t2 c
    45.                 pRealArray2=(luRealArray *)SearchKey((char *)&((xx+1)->x),sizeof(luVOID),luDynData_realarray);4 r: V3 r3 ]/ \. n  R
    46.                 if(!pRealArray1 || !pRealArray2) break;        //对象句柄无效,不是实数数组
    47. . h\\" e+ M+ D& d& X1 O; }
    48.                 if(pRealArray1->DimLen!=2 || pRealArray2->DimLen!=2) break;        //不是二维实数数组(矩阵)
    49. - h  V, T: R4 q2 `4 `8 w; t
    50.                 if(pRealArray1->Dim[1]!=pRealArray2->Dim[0]) break;        //维数不匹配/ r& s+ k* V: C3 p
    51.                 pRealArray3=(luRealArray *)NewSysObj(luDynData_realarray,pRealArray1->Dim[0]*pRealArray2->Dim[1],2);        //创建矩阵对象5 V8 G$ B$ v# o% A0 B
    52.                 if(!pRealArray3) break;; f, ?7 K$ q. J5 Z- D\\" S
    53.                 pRealArray3->Dim[0]=pRealArray1->Dim[0]; pRealArray3->Dim[1]=pRealArray2->Dim[1];        //设置矩阵维数大小0 i8 k5 J8 R. G- V8 `
    54.                 pa=pRealArray1->Array; pb=pRealArray2->Array; pc=pRealArray3->Array;
    55. : y; C2 r) W, ^7 q' ~7 I% C' K
    56.                 m=pRealArray1->Dim[0]; n=pRealArray1->Dim[1]; k=pRealArray2->Dim[1];
    57. 5 i6 ?3 r1 q9 Q0 R  b2 m. r. D% `
    58.                 for(i=0; i<m; i++)        //矩阵乘( R; U1 O7 O5 R5 P\\" ?
    59.                 {4 A- `1 d# w2 T: f6 O1 S+ S/ I
    60.                         for(j=0; j<k; j++)2 Z! ~7 o! j6 d6 j
    61.                         {9 Z% D+ Z\\" `/ {8 w
    62.                                 u=i*k+j; pc[u]=0.0;
    63. # K& h/ {) @$ Q8 y% z
    64.                                 for (v=0; v<n; v++)
    65. 7 S5 h5 r! }* x' E! j0 _- I
    66.                                 {
    67. 5 k8 i0 U( X1 I4 _3 J
    68.                                         pc[u]=pc[u]+pa[i*n+v]*pb[v*k+j];& a; [8 m& |6 a, T7 g' a7 N
    69.                                 }
    70. + i2 {. F  {  e# X\\" h0 ~
    71.                         }# p- M0 I\\" d: C3 Y1 m9 U
    72.                 }
    73. 1 h# c+ r* T; f$ g\\" s- B\\" I8 t
    74.                 FunReObj(hFor);        //告诉Lu,返回一个动态对象2 i1 V7 j2 f; ], G; f* E0 ~
    75.                 a.BType=luDynData_realarray; a.VType=Matrix; a.x=0; *(luVOID *)&(a.x)=(luVOID)pRealArray3;
    76. 5 l& U4 X\\" p2 p3 t2 z# j
    77.                 break;
    78.   B  H2 g/ m( V# V
    79.         case 25:        //重载运算符.*
    80. ; C) V! s. t' E0 \7 F1 c1 z3 C) g
    81.                 pRealArray1=(luRealArray *)SearchKey((char *)&(xx->x),sizeof(luVOID),luDynData_realarray);. x, y1 C$ M7 ^. y
    82.                 pRealArray2=(luRealArray *)SearchKey((char *)&((xx+1)->x),sizeof(luVOID),luDynData_realarray);
    83. 3 g/ h/ O& d$ M+ ]& K% w/ S. O) C! W
    84.                 if(!pRealArray1 || !pRealArray2) break;        //对象句柄无效,不是实数数组
    85. 9 C& l1 x2 H7 ~8 d4 C6 ?6 O
    86.                 if(pRealArray1->DimLen!=2 || pRealArray2->DimLen!=2) break;        //不是二维实数数组(矩阵)
    87. ( z6 }) b* k/ T& B$ k3 O; j4 T: q
    88.                 if(pRealArray1->Dim[0]!=pRealArray2->Dim[0] || pRealArray1->Dim[1]!=pRealArray2->Dim[1]) break;        //维数不相同6 m* G) N6 Q0 z; |\\" L
    89.                 pRealArray3=(luRealArray *)NewSysObj(luDynData_realarray,pRealArray1->ArrayLen,2);        //创建矩阵对象/ V3 X3 r) M, E6 U
    90.                 if(!pRealArray3) break;
    91. * E; S\\" Y) m% ?2 J! j# i
    92.                 pRealArray3->Dim[0]=pRealArray1->Dim[0]; pRealArray3->Dim[1]=pRealArray1->Dim[1];        //设置矩阵维数大小1 d* q6 a0 ^; b! L4 t1 L4 A
    93.                 for(i=0;i<pRealArray1->ArrayLen;i++) pRealArray3->Array[i]=pRealArray1->Array[i]*pRealArray2->Array[i];//矩阵点乘* Q# s0 z  k4 m7 {2 w' }! A
    94.                 FunReObj(hFor);        //告诉Lu,返回一个动态对象
    95. % b! Q6 l) N+ Z  O
    96.                 a.BType=luDynData_realarray; a.VType=Matrix; a.x=0; *(luVOID *)&(a.x)=(luVOID)pRealArray3;
    97. 8 W/ p+ f5 |+ P% k9 A1 `! M) D
    98.                 break;
    99. ( r7 |' m; H5 V9 o' h0 X
    100.         case 46:        //重载函数new
    101. + Y; z0 d: n7 X0 H
    102.                 a=ExeOperator(mm,xx,hFor,theOperator,luDynData_realarray);        //直接调用基本类型luDynData_realarray的new函数- Q) @\\" c. s% e7 D
    103.                 if(a.VType==luDynData_realarray) a.VType=Matrix;        //设置扩展类型为自定义的Matrix类型
    104. + [- U9 K9 a/ M0 {: N\\" a- v
    105.                 break;
    106. - A. c6 I0 b( _
    107.         case 49:        //重载函数o( d% ~- ?* F* C% p. d  h
    108.                 pMessage=(luMessage)SearchKey("\0\0\0\0",sizeof(luVOID),luPubKey_User);
    109. . ^/ s; h- S. }1 U
    110.                 if(!pMessage) break;/ n% v* `3 t* U6 v
    111.                 pRealArray1=(luRealArray *)SearchKey((char *)&(xx->x),sizeof(luVOID),luDynData_realarray);& u8 n; {4 w1 ]: r( d- h' V
    112.                 if(!pRealArray1) break;        //对象句柄无效,不是实数数组
    113. 8 e: |! O0 K6 Q( J% i8 u) T  J\\" i3 x
    114.                 if(pRealArray1->DimLen!=2) break;        //不是二维实数数组(矩阵)( w, j. F6 h& A
    115.                 pa=pRealArray1->Array;* g+ P* T. b. ]& `3 g2 |( m
    116.                 m=pRealArray1->Dim[0]; n=pRealArray1->Dim[1]; k=0;
    117. 6 U. c* Y$ T6 y4 y. l
    118.                 for(i=0; i<m; i++)        //输出矩阵. N# \9 _% X2 o' V4 `, E
    119.                 {( S0 p4 H3 p& t
    120.                         pMessage(L"\r\n"); k+=2;: J6 ]  k1 j0 u, D
    121.                         for(j=0; j<n; j++)
    122.   z4 B! ]% ]9 X* {5 H
    123.                         {
    124. ) S4 T2 o9 X4 V! D4 G
    125.                                 _gcvt_s(chNum,pa[i*n+j],16);
    126. - X4 R% X, `; F* F; `
    127.                                 for(u=0;chNum[u];u++) {wchNum[u]=chNum[u]; k++;}
    128. ) ^+ f, j; ?; }- T* a1 k
    129.                                 wchNum[u]='\0';
    130. ) Y4 X& g: g4 g# i) v% V/ A
    131.                                 pMessage(wchNum); pMessage(L"  "); k+=2;, L  `1 q) l. ~5 D; @- E1 w
    132.                         }/ G  a. i+ }* x4 F. I- m6 f
    133.                 }
    134. # P+ u0 I- H# i7 d
    135.                 pMessage(L"\r\n"); k+=2;/ }# n5 N' s% y+ p9 o4 L
    136.                 a.BType=luStaData_int64; a.VType=luStaData_int64; a.x=k;        //按函数o的要求,返回输出的字符总数
    137. + s0 S% ?3 S2 Z
    138.                 break;
    139. $ E8 N& @6 H# z' g2 |# T
    140.         default:
    141. & M, H\\" F# [5 A9 R* v
    142.                 break;
    143. + c' b5 l- O0 u% L; g. B* ^0 y
    144.         }4 l( ^: o- M: V4 v+ d4 z
    145.         return a;
    146. 4 A6 p0 ?( `5 d\\" Z7 X/ a
    147. }7 y4 J3 ~; i8 ]  ?* D
    148. void main(void)+ z( p& Q& I4 V1 Y
    149. {\\" i2 L# ~6 y2 T9 r+ _# h
    150.         void *hFor;                //表达式句柄1 L3 t: @' v. P+ X\\" ]
    151.         luINT nPara;                //存放表达式的自变量个数' Q4 Q0 M( q2 J
    152.         LuData *pPara;                //存放输入自变量的数组指针
    153. + y; ?& C8 N: C
    154.         luINT ErrBegin,ErrEnd;        //表达式编译出错的初始位置和结束位置
    155. ) G' x4 c/ I+ G* B- @2 D8 }$ \6 s& s
    156.         int ErrCode;                //错误代码, Z9 ~5 y6 Q. v* u
    157.         void *v;: z7 l' f& ~  w6 U0 U) N9 x
    158.         wchar_t ForStr[]=L"o{new[matrix,2,3,data: 0.,1.,2.;3.,4.,5.]*new[matrix,3,2,data: 1.,2.;3.,4.;5.,6.]}";//字符串表达式,矩阵乘* ]4 c/ J: A9 Q2 o0 k0 a: E
    159.         //wchar_t ForStr[]=L"o{new[matrix,2,3,data: 0.,1.,2.;3.,4.,5.].*new[matrix,2,3,data: 1.,2.,3.;4.,5.,6.]}";//字符串表达式,矩阵点乘
    160. $ K6 y* n6 L) c4 q' F
    161.         LuData Val;
    162. \\" w# `* ]) i( i$ m$ g\\" P5 D
    163.         if(!InitLu()) return;        //初始化Lu
    164. 5 M/ n, \2 x6 A\\" f
    165.         while(LockKey(Matrix,DelMatrix,OpMatrix)){Matrix++;}        //锁定一个键,用于存储矩阵扩展类型6 S3 q5 L; o2 J; C4 F1 B
    166. 0 f4 `, G& {  U
    167.         Val.BType=luStaData_int64; Val.VType=luStaData_int64; Val.x=Matrix;        //定义整数常量
    168. ! `\\" q5 S% v& ?$ D$ n
    169.         SetConst(L"matrix",&Val);        //设置整数常量, j/ y( p4 t0 _
    170.         InsertKey("\0\0\0\0",4,luPubKey_User,LuMessage,NULL,NULL,1,v); //使Lu运行时可输出函数信息. g, E) y+ e- t
    171.         wcout.imbue(locale("chs"));        //设置输出的locale为中文
    172. + e6 X\\" p' t% \\\" N+ p9 s
    173.   
    174. 6 V' g0 f# V6 z* ^$ m1 E, w
    175.         ErrCode=LuCom(ForStr,0,0,0,hFor,nPara,pPara,ErrBegin,ErrEnd); //编译表达式
    176. 0 n, |' N  T1 N* |2 P
    177.         if(ErrCode)' d6 K. j+ u- X+ x$ }/ e
    178.         {\\" \  E: B: ^/ S2 t/ G! [, q
    179.                 wcout<<L"表达式有错误!错误代码:"<<ErrCode<<endl;
    180. \\" O! ~7 F# S3 E9 X! p9 g
    181.         }- r8 s0 T. M: T+ Z6 h  R0 C
    182.         else3 G8 O1 K+ A9 ~, [' D' Q$ ~8 Q9 p
    183.         {
    184.   \2 X- }6 f; J7 r
    185.                 LuCal(hFor,pPara);        //计算表达式的值
    186. ' c. V1 ^# D1 n2 ^9 j7 f2 P
    187.         }/ p1 Y0 k1 e+ \- i
    188.         LockKey(Matrix,NULL,OpMatrix);//解锁键Matrix,本例中,该函数可以不用  `* T! D7 K/ F5 E5 _) g8 m
    189.         FreeLu();                        //释放Lu. y0 j0 _5 I# z/ p8 M& f
    190. }
    习题:
    ( @% ?0 p9 y! j9 A/ ]8 Y. C3 U4 x9 F( b% W6 q4 V$ ^8 G
        (1)自定义矩阵的加、减、左除、右除、点左除等运算,自编测试字符串代码,重新编译运行程序,观察计算结果。 ' s5 x9 |: X: }
    " a. O; |" v$ B% s! c+ a4 L5 A
        (2)小矩阵乘效率测试。编译运行以下Lu字符串代码:
    1. main(:a,b,c,d,t,i)=
      : X7 X2 u6 y8 `
    2.     a=new[matrix,2,2,data:1.,2.,2.,1.],: @/ f\" g+ h\" k  W
    3.     b=new[matrix,2,2,data:2.,1.,1.,2.],
      ( G- C8 i) l' m5 T4 L8 _8 B
    4.     c=new[matrix,2,2,data:2/3.,-1/3.,-1/3.,2/3.],. R% P) s# k. t/ c# A
    5.     t=clock(),
      & N1 O& |+ [: V4 l# Y9 Z
    6.     d=a*b, i=0, while{i<1000000, d=d*c*b, i++},\" Y- T\" B2 \' {& J4 {1 L
    7.     o{d, "time=",[clock()-t]/1000.," seconds.\r\n"}
    复制代码
    C/C++中的字符串定义为:
    1. wchar_t ForStr[]=L"main(:a,b,c,d,t,i)= a=new[matrix,2,2,data:1.1,2.,2.,1.], b=new[matrix,2,2,data:2.,1.,1.,2.], c=new[matrix,2,2,data:2/3.,-1/3.,-1/3.,2/3.], t=clock(), d=a*b, i=0, while{i<1000000, d=d*c*b, i++}, o{d, \"time=\",[clock()-t]/1000.,\" seconds.\r\n\"}";//字符串表达式
    复制代码
    结果:
    1. 4. 5.
      # _& e( u: W! Y. i' W8 _% l
    2. 5. 4.0 M( o' X) ~/ G  L7 W
    3. time=0.875 seconds.
      3 f. F3 t* D$ a/ X! a4 \! i6 M
    4. 请按任意键继续. . .
    复制代码
    Matlab 2009a 代码:
    1. a=[1.,2.;2.,1.];
      ) ]\" H5 U- ?, p) P7 H
    2. b=[2.,1.;1.,2.];
      6 x. h! [8 @+ E/ z\" Z
    3. c=[2/3.,-1/3.;-1/3.,2/3.];
      ' M: V# _! ^% G
    4. tic,' g+ Y, [+ t\" ^* v  @8 }' ?
    5. d=a*b;
      . r: a- g$ O) U5 P# e+ k
    6. for i=1:10000009 G  ?9 Z\" F- e
    7.     d=d*c*b;
      . L! M. c3 J- M  {7 i
    8. end/ }$ V. j\" d% ]' P
    9. d,- S8 u( Q4 v& L1 y; J: N\" k- t
    10. toc
    复制代码
    结果:
    1. d =9 ^3 |  K1 `# k  G\" I) y- S' j
    2.      4     5
      4 V6 \9 I  H5 d6 ^- T0 y, F
    3.      5     4. F! p3 B; L' e2 o( V
    4. Elapsed time is 2.903034 seconds.
    复制代码
    本例矩阵乘效率测试,Lu的速度超过了Matlab,主要在于Lu有更高的动态对象管理效率。
    ! M/ M. h9 v' _- d# W
    zan
    转播转播0 分享淘帖0 分享分享0 收藏收藏0 支持支持0 反对反对0 微信微信
    您需要登录后才可以回帖 登录 | 注册地址

    qq
    收缩
    • 电话咨询

    • 04714969085
    fastpost

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

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

    蒙公网安备 15010502000194号

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

    GMT+8, 2026-4-14 14:35 , Processed in 0.424816 second(s), 55 queries .

    回顶部