QQ登录

只需要一步,快速开始

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

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

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

45

主题

3

听众

282

积分

升级  91%

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

    [LV.1]初来乍到

    跳转到指定楼层
    1#
    发表于 2011-10-23 09:37 |只看该作者 |倒序浏览
    |招呼Ta 关注Ta
        本例中,我们将基于系统内置实数数组创建矩阵(matrix)类型,即:基本类型为luDynData_realarray(标识实数数组),扩展类型为matrix(标识矩阵)。为了简单,我们仅处理二维实数数组即矩阵类型。7 \8 G$ p2 ~% }5 W* `- C: b, i4 j. i

    - l- h9 U+ g& C9 [    基本要点:
    8 g0 m& H9 g% e0 ~! N! @4 w& Y2 i7 s' z: L' j- P* n9 P: Q* p
        (1)为扩展类型matrix编写运算符重载函数OpMatrix。
    & x# x3 ~1 ]  @0 f0 p: z* X" O# F  J
        (2)用函数LockKey将重载函数OpMatrix注册到Lu,锁定的键的类型即为matrix,要注册为常量,以便于使用。
    / O  X4 v& o' q/ G0 X( |, G! y
    ; e: C! Z* m& x3 ]4 D    (3)为扩展类型matrix编写其他操作函数(本例未提供)。* Z; V4 g" s1 R0 F

    ) e3 m- g) q3 I    (4)用函数LockKey解锁键matrix(本例中,程序退出时会自动解锁,故可以不用)。
    1. #include <windows.h>
    2. 2 f6 L: u6 Q+ y0 h
    3. #include <iostream>
    4. , Q& H6 N) V3 Q- f* P5 {
    5. #include <math.h>
    6. , q1 s! b1 l7 X. B, j\\" |. u
    7. #include "lu32.h"
    8. 0 ?/ r, R7 f7 M  q8 E4 M# A

    9.   D0 R, }( j) P( F2 |  b
    10. #pragma comment( lib, "lu32.lib" )
    11. % }! s) D9 B\\" x/ R$ {

    12. ; ]& u/ u5 B* H# o3 h* m+ {) T
    13. using namespace std;
    14. : z. J\\" i* p+ a9 h7 e  W) @  A
    15. ' v& b6 ]; C$ ^* D8 N. b5 P9 a% I
    16. luKEY Matrix=-1000;        //标识矩阵类型,最终的Matrix由LockKey决定
    17. 4 ?* {% H. m- A0 J

    18. ! a( V; Q2 a% V
    19. void _stdcall LuMessage(wchar_t *pch)//输出动态库信息,该函数注册到Lu,由Lu二级函数调用 7 E/ {/ w( U3 D' c9 d. s
    20. {6 B$ J$ B+ f+ s7 ^$ l3 |2 F) Q
    21.         wcout<<pch;3 k: o# X: ~# t2 N\\" [( K# V
    22. }
    23. ! Z( k# ~5 Q; ?) J+ A% Z2 f: Q
    24. void _stdcall DelMatrix(void *me)        //用于LockKey函数,因为是基于系统内置实数数组创建矩阵,故该函数什么也不做- P$ d7 r4 ^4 M- m& y# r- n
    25. {& W( G( {8 n, c\\" I. }  Y
    26. }9 D, d3 D. H8 _% R- e# e1 L* O- i
    27. LuData _stdcall OpMatrix(luINT mm,LuData *xx,void *hFor,int theOperator)        //运算符重载函数,用于LockKey函数5 c' A1 ?0 Q+ ]+ V; q
    28. {
    29. - f4 j) J6 q* E9 j
    30.         LuData a;5 u/ a2 u& M( e
    31.         luRealArray *pRealArray1,*pRealArray2,*pRealArray3;
    32. 0 Y7 E3 r! Q/ K/ ]7 [\\" s
    33.         luVOID i,j,k,m,n,u,v;
    34. ( o! I( z/ O. s- n3 d! m% V
    35.         double *pa,*pb,*pc;' Y: J' c* [, H7 p# O) ~# w
    36.         luMessage pMessage;* \4 s9 ^+ n' \' r5 a
    37.         wchar_t wchNum[32];% U# `\\" S$ U# T# A5 b  E
    38.         char chNum[32];
    39. % ^  g- X\\" A. A
    40.         a.BType=luStaData_nil; a.VType=luStaData_nil; a.x=0;5 P' P/ Y: c0 b6 k  [1 G
    41.         switch(theOperator)6 K% [, V9 Z6 G\\" E9 u) B1 r3 F
    42.         {
    43. . c, I0 n% R; ]6 r! W
    44.         case 2:        //重载运算符*
    45.   p( r# Z- x% g) w' q( n6 E5 M% c
    46.                 pRealArray1=(luRealArray *)SearchKey((char *)&(xx->x),sizeof(luVOID),luDynData_realarray);2 M- u' e5 `3 U# Q+ d6 h! j; q) u
    47.                 pRealArray2=(luRealArray *)SearchKey((char *)&((xx+1)->x),sizeof(luVOID),luDynData_realarray);
    48. 4 M0 _4 P2 z1 e+ E7 a% u
    49.                 if(!pRealArray1 || !pRealArray2) break;        //对象句柄无效,不是实数数组7 S. d7 G( ~+ T9 x1 }
    50.                 if(pRealArray1->DimLen!=2 || pRealArray2->DimLen!=2) break;        //不是二维实数数组(矩阵)( ~7 H: \% ]2 z\\" @2 Y
    51.                 if(pRealArray1->Dim[1]!=pRealArray2->Dim[0]) break;        //维数不匹配- @6 ]9 ^7 f0 _9 T3 T# g4 s' F/ ~. z* x$ P+ o
    52.                 pRealArray3=(luRealArray *)NewSysObj(luDynData_realarray,pRealArray1->Dim[0]*pRealArray2->Dim[1],2);        //创建矩阵对象
    53.   ]( O. P) [# h; i. u  O3 h  K
    54.                 if(!pRealArray3) break;
    55. ) h. t: ]8 J\\" X/ {( j
    56.                 pRealArray3->Dim[0]=pRealArray1->Dim[0]; pRealArray3->Dim[1]=pRealArray2->Dim[1];        //设置矩阵维数大小6 G, q7 o/ M# Q$ ]8 c
    57.                 pa=pRealArray1->Array; pb=pRealArray2->Array; pc=pRealArray3->Array;
    58. 3 G+ T\\" s( r  c0 P0 K: L; Z- b; \
    59.                 m=pRealArray1->Dim[0]; n=pRealArray1->Dim[1]; k=pRealArray2->Dim[1];# v& K& N1 S* p8 s
    60.                 for(i=0; i<m; i++)        //矩阵乘, @1 L\\" u3 E  C9 y' B+ Z
    61.                 {6 t2 q! I3 O/ S. N  Z/ [9 z/ g
    62.                         for(j=0; j<k; j++)7 K2 R3 T  I0 q% Z* Q
    63.                         {
    64. : _7 D# i7 R- j  F
    65.                                 u=i*k+j; pc[u]=0.0;! {, P6 V5 Q3 s1 T
    66.                                 for (v=0; v<n; v++)- D6 |0 i, B3 W$ u
    67.                                 {
    68. 7 o0 C+ ]- k/ w; n
    69.                                         pc[u]=pc[u]+pa[i*n+v]*pb[v*k+j];
    70. \\" H5 f8 E. K7 A. B3 w: K
    71.                                 }9 A9 y  Y/ B9 Q; Y
    72.                         }
    73. ! y; ]7 r7 z) @7 i/ G9 }/ Q7 v, k
    74.                 }
    75. $ v/ Q; @: o+ M
    76.                 FunReObj(hFor);        //告诉Lu,返回一个动态对象
    77. \\" w* a- N  n0 ^\\" B) v
    78.                 a.BType=luDynData_realarray; a.VType=Matrix; a.x=0; *(luVOID *)&(a.x)=(luVOID)pRealArray3;
    79. & r) m1 ?. a* B' T* Q3 h
    80.                 break;\\" W5 q0 @* ]8 M& Z% F2 Q( J! [' i
    81.         case 25:        //重载运算符.*$ O/ _; [5 h% ]4 c6 v; [' p
    82.                 pRealArray1=(luRealArray *)SearchKey((char *)&(xx->x),sizeof(luVOID),luDynData_realarray);( Q\\" |# N$ C, Q' i; y
    83.                 pRealArray2=(luRealArray *)SearchKey((char *)&((xx+1)->x),sizeof(luVOID),luDynData_realarray);
    84. \\" J8 N3 T8 W& k6 v5 S6 z
    85.                 if(!pRealArray1 || !pRealArray2) break;        //对象句柄无效,不是实数数组
    86. 9 ^0 z  Z/ j- T1 o4 D- Q
    87.                 if(pRealArray1->DimLen!=2 || pRealArray2->DimLen!=2) break;        //不是二维实数数组(矩阵)
    88. \\" a2 ~! y7 h5 s3 s# C
    89.                 if(pRealArray1->Dim[0]!=pRealArray2->Dim[0] || pRealArray1->Dim[1]!=pRealArray2->Dim[1]) break;        //维数不相同
    90. / l/ _4 f6 O9 P& w* M( e
    91.                 pRealArray3=(luRealArray *)NewSysObj(luDynData_realarray,pRealArray1->ArrayLen,2);        //创建矩阵对象
    92. + j# \0 E. G2 M6 ~! D9 w
    93.                 if(!pRealArray3) break;
    94. 7 [+ c, @7 x( Z- d! F  z
    95.                 pRealArray3->Dim[0]=pRealArray1->Dim[0]; pRealArray3->Dim[1]=pRealArray1->Dim[1];        //设置矩阵维数大小2 y/ y6 k4 G8 t, V: x; K# Z( `5 z
    96.                 for(i=0;i<pRealArray1->ArrayLen;i++) pRealArray3->Array[i]=pRealArray1->Array[i]*pRealArray2->Array[i];//矩阵点乘# S$ A. w# H; ?' C& E
    97.                 FunReObj(hFor);        //告诉Lu,返回一个动态对象\\" G. Z4 L6 }  U  X0 t
    98.                 a.BType=luDynData_realarray; a.VType=Matrix; a.x=0; *(luVOID *)&(a.x)=(luVOID)pRealArray3;7 Q1 m6 p. g; O' Q
    99.                 break;
    100. 6 j) l8 a6 B5 X0 ^4 o$ N
    101.         case 46:        //重载函数new( l( I# x9 Q$ p& \& ^
    102.                 a=ExeOperator(mm,xx,hFor,theOperator,luDynData_realarray);        //直接调用基本类型luDynData_realarray的new函数
    103. 3 P' r4 Q' Z( b$ C
    104.                 if(a.VType==luDynData_realarray) a.VType=Matrix;        //设置扩展类型为自定义的Matrix类型% J' E# n% }2 U1 M+ c\\" N
    105.                 break;! F\\" ^+ z+ P2 o3 [' n# Y
    106.         case 49:        //重载函数o
    107. 1 H8 _- E8 G( a) j
    108.                 pMessage=(luMessage)SearchKey("\0\0\0\0",sizeof(luVOID),luPubKey_User);7 P2 N; v7 u$ i, r
    109.                 if(!pMessage) break;
    110. 7 ~; k: L! d0 c4 n
    111.                 pRealArray1=(luRealArray *)SearchKey((char *)&(xx->x),sizeof(luVOID),luDynData_realarray);) G. `3 z' A$ g- i9 _
    112.                 if(!pRealArray1) break;        //对象句柄无效,不是实数数组
    113. 0 b) z  ~  E6 s4 ], [. [
    114.                 if(pRealArray1->DimLen!=2) break;        //不是二维实数数组(矩阵)7 \( k; @; ~, S& M' g$ I
    115.                 pa=pRealArray1->Array;
    116. 6 R, A2 E) q: S: ^4 g# d5 ?& Z
    117.                 m=pRealArray1->Dim[0]; n=pRealArray1->Dim[1]; k=0;
    118. 9 v& a* C% K; @4 ?  q
    119.                 for(i=0; i<m; i++)        //输出矩阵0 o: ^7 i0 p7 X7 m# s\\" j9 c1 F# `
    120.                 {5 x- A4 k+ E& R
    121.                         pMessage(L"\r\n"); k+=2;
    122. : g- v! G\\" z; I  r4 x- J2 b
    123.                         for(j=0; j<n; j++)2 @4 X6 H\\" y) Y4 S. v- o
    124.                         {
    125. ) p& I1 X7 v+ ~
    126.                                 _gcvt_s(chNum,pa[i*n+j],16);
    127. 0 P$ z9 v( M* C
    128.                                 for(u=0;chNum[u];u++) {wchNum[u]=chNum[u]; k++;}/ a7 u( h' Y4 l- Q( G5 I
    129.                                 wchNum[u]='\0';3 D5 a0 `\\" O( d& W1 K  ~
    130.                                 pMessage(wchNum); pMessage(L"  "); k+=2;
    131. % k4 X( U7 R$ o% D
    132.                         }- p/ [: @: ^* v
    133.                 }
    134. \\" @* }+ p+ O+ b8 T: ]9 b
    135.                 pMessage(L"\r\n"); k+=2;4 `8 E3 L) i  O6 [\\" {+ D9 Q
    136.                 a.BType=luStaData_int64; a.VType=luStaData_int64; a.x=k;        //按函数o的要求,返回输出的字符总数
    137. ; B$ h: U\\" X/ K! k' s& M8 c
    138.                 break;3 W6 O% A2 B! d; d# G0 h+ E
    139.         default:
    140. 0 T' P/ j! M4 j# X
    141.                 break;  Z6 _) S2 q: c. u5 Q& @* k- e
    142.         }5 ?3 u( P2 u2 w* Q: J
    143.         return a;
    144. ) o+ M) a\\" u( g6 z5 c. t: _: q
    145. }9 R0 ^3 k2 J9 H, c6 }
    146. void main(void)
    147. ! F9 j' {- {0 `) m; x5 g: [' m
    148. {2 [; `/ p  j+ m+ _6 l! P
    149.         void *hFor;                //表达式句柄% C' S* S) _5 p
    150.         luINT nPara;                //存放表达式的自变量个数$ P5 L' }: z7 E/ ]/ k# X
    151.         LuData *pPara;                //存放输入自变量的数组指针) \+ N& W: @4 u! Q- |
    152.         luINT ErrBegin,ErrEnd;        //表达式编译出错的初始位置和结束位置/ b6 y- \1 |$ J
    153.         int ErrCode;                //错误代码
    154. , Z\\" P9 `. ~* b% Z6 n. ?! |
    155.         void *v;8 L! \, n& ?7 N4 a# J
    156.         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.]}";//字符串表达式,矩阵乘- z$ W/ B& L  a: S
    157.         //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.]}";//字符串表达式,矩阵点乘
    158.   O% c9 t; |' ]4 _; z! T+ J7 f
    159.         LuData Val;
    160. , [6 L8 ?1 D6 M' Q
    161.         if(!InitLu()) return;        //初始化Lu5 f: U- p0 G! X
    162.         while(LockKey(Matrix,DelMatrix,OpMatrix)){Matrix++;}        //锁定一个键,用于存储矩阵扩展类型/ Y; I$ D1 h  P9 V

    163. 4 G\\" E0 x: r* K
    164.         Val.BType=luStaData_int64; Val.VType=luStaData_int64; Val.x=Matrix;        //定义整数常量: E; K8 P) o\\" ?% Y$ T* ~) f. N\\" q* P
    165.         SetConst(L"matrix",&Val);        //设置整数常量* f. H' l/ j9 O: F. H' g
    166.         InsertKey("\0\0\0\0",4,luPubKey_User,LuMessage,NULL,NULL,1,v); //使Lu运行时可输出函数信息
    167. 3 z  d& j* v( q# q8 C
    168.         wcout.imbue(locale("chs"));        //设置输出的locale为中文
    169. # L, r0 {% W: {0 Z# r- `! a
    170.   
    171. ' Y8 f& _\\" D' `7 j! D. j\\" i
    172.         ErrCode=LuCom(ForStr,0,0,0,hFor,nPara,pPara,ErrBegin,ErrEnd); //编译表达式
    173. ; g( S; ~$ V5 a2 _; M
    174.         if(ErrCode)- a/ x& k% z0 a7 Q# j( k
    175.         {
    176. 7 j7 {\\" w# @& c
    177.                 wcout<<L"表达式有错误!错误代码:"<<ErrCode<<endl;% u' K/ ~0 P) G2 R6 G, J
    178.         }& e+ o- J9 ]6 q
    179.         else  X# f6 D/ i( u3 }, T\\" n
    180.         {# t1 @5 k\\" ^& _1 n- |; _' [. B; E# A
    181.                 LuCal(hFor,pPara);        //计算表达式的值6 A  j8 \- @& F- I4 ]
    182.         }
    183. + t. n; P) c; b' u4 ^8 p4 s! l
    184.         LockKey(Matrix,NULL,OpMatrix);//解锁键Matrix,本例中,该函数可以不用
    185. 1 W2 _1 Z6 Y* u
    186.         FreeLu();                        //释放Lu
    187. \\" A( u0 Q2 U! X0 }
    188. }
    习题:. {1 S. x5 X" m- |% n
    & \$ B. k/ T3 n1 s
        (1)自定义矩阵的加、减、左除、右除、点左除等运算,自编测试字符串代码,重新编译运行程序,观察计算结果。 , S) {2 j; W; [9 @; z2 m5 ?

    / M8 X1 q, C: r& e. Z: w    (2)小矩阵乘效率测试。编译运行以下Lu字符串代码:
    1. main(:a,b,c,d,t,i)=
      % z/ R1 t! r: w2 f
    2.     a=new[matrix,2,2,data:1.,2.,2.,1.],
      : B/ s  p' D1 r# j+ l6 S8 Y
    3.     b=new[matrix,2,2,data:2.,1.,1.,2.],, m( @5 e8 t, E* H3 }
    4.     c=new[matrix,2,2,data:2/3.,-1/3.,-1/3.,2/3.],+ |5 p/ p1 k0 {% \9 o# Y8 ^
    5.     t=clock(),6 K/ I6 T* i; f5 u& u8 _+ `/ R
    6.     d=a*b, i=0, while{i<1000000, d=d*c*b, i++},
      ' P* ]- v' ?+ \: l0 B/ J
    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.3 Q* s* w( ]3 S  g& J  W9 w
    2. 5. 4.
      $ S, g& P: X; o- E  ]
    3. time=0.875 seconds.
      \" s7 \& @9 i2 l
    4. 请按任意键继续. . .
    复制代码
    Matlab 2009a 代码:
    1. a=[1.,2.;2.,1.];
      # G# L+ ^7 w$ A$ J+ P# ?4 Q! u; y
    2. b=[2.,1.;1.,2.];
      ) @+ E# i\" y( v. ^1 h' s  }2 r; t
    3. c=[2/3.,-1/3.;-1/3.,2/3.];( p6 c& e% {$ x- v; k
    4. tic,
      $ B9 j3 s) Y7 }\" d4 Z/ x# u
    5. d=a*b;( L, L7 }4 R! n. Q7 G
    6. for i=1:1000000+ ?+ f1 A) u  b3 v6 C
    7.     d=d*c*b;1 ]/ |9 B# U8 i5 o' {& T' l
    8. end
      % p9 h2 X; {* q! Y5 W5 [, C
    9. d,0 v) u- H* c/ L6 O
    10. toc
    复制代码
    结果:
    1. d =
      1 o' Z* n* r5 j+ q) G+ R' \4 ?
    2.      4     58 z9 I9 i9 ~, ]1 a9 s; |7 K
    3.      5     4
      1 I) P5 N) ^# Z
    4. Elapsed time is 2.903034 seconds.
    复制代码
    本例矩阵乘效率测试,Lu的速度超过了Matlab,主要在于Lu有更高的动态对象管理效率。8 s5 o- M& A1 j' b( f. x
    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-6-13 02:05 , Processed in 0.461979 second(s), 53 queries .

    回顶部