QQ登录

只需要一步,快速开始

 注册地址  找回密码
查看: 8904|回复: 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(标识矩阵)。为了简单,我们仅处理二维实数数组即矩阵类型。% U( c$ {9 j1 ^, p0 z
    2 {% K0 @  Z6 j% h4 f. J0 u& ?" M
        基本要点:' b0 x( h  w7 p2 ~
    1 W) h' E* i7 [! ]" {: h3 M, q- j! E
        (1)为扩展类型matrix编写运算符重载函数OpMatrix。
    ! k0 H* f3 O7 e$ K
    , a$ d! P) X& M( c+ M7 ~    (2)用函数LockKey将重载函数OpMatrix注册到Lu,锁定的键的类型即为matrix,要注册为常量,以便于使用。
    6 ~: `  ~  C- M1 e4 H' N( }* x1 u# z' Y1 F
        (3)为扩展类型matrix编写其他操作函数(本例未提供)。7 D2 L9 H3 a. P4 `

      ?, j3 C* x: D. Z8 V    (4)用函数LockKey解锁键matrix(本例中,程序退出时会自动解锁,故可以不用)。
    1. #include <windows.h>
    2. % ]- s! D. U% T  L
    3. #include <iostream>
    4. 8 d, O1 S+ x7 g% L- ]& x/ W
    5. #include <math.h>! h; p9 ?: A( K# |& X/ ^
    6. #include "lu32.h"
    7. + C5 Z) \$ X  Q# `# u  x4 o1 P

    8. # X3 V! D2 Z& N( {! R# S$ T+ m
    9. #pragma comment( lib, "lu32.lib" )! [- _! \  b/ G+ k\\" O& R
    10. 8 m2 D+ b. z1 a
    11. using namespace std;) r1 G0 V( f/ n
    12. % P; M' ^# U/ J$ v0 E
    13. luKEY Matrix=-1000;        //标识矩阵类型,最终的Matrix由LockKey决定
    14. 5 ^8 z# K% v9 B2 i: x

    15. 7 i# L/ ^5 [* U7 A6 ~\\" G% D8 |
    16. void _stdcall LuMessage(wchar_t *pch)//输出动态库信息,该函数注册到Lu,由Lu二级函数调用
    17. ( u, N+ |0 q  a- a6 P) l5 l$ d; f
    18. {; a' |% L# M2 {  ]
    19.         wcout<<pch;5 ]: d' ]- R4 a4 B
    20. }( ~+ u5 g- R1 ^' g
    21. void _stdcall DelMatrix(void *me)        //用于LockKey函数,因为是基于系统内置实数数组创建矩阵,故该函数什么也不做
    22. 9 k, l, t% L  ^7 A& l* K& i! ~
    23. {
    24. ; a* y! D+ G2 R7 ^
    25. }
    26. 7 ^& f2 P0 `  D: m
    27. LuData _stdcall OpMatrix(luINT mm,LuData *xx,void *hFor,int theOperator)        //运算符重载函数,用于LockKey函数4 \  ~% q. |) k( P$ C
    28. {
    29. 8 Q, [8 t( h0 b& e. t
    30.         LuData a;0 W' c& }7 B. v# t) Z6 G8 Y
    31.         luRealArray *pRealArray1,*pRealArray2,*pRealArray3;8 \: _, h- ?# v' _) B+ M
    32.         luVOID i,j,k,m,n,u,v;
    33. 5 G+ t: `8 Y* g3 p& r. y4 G
    34.         double *pa,*pb,*pc;9 S/ J4 U1 _4 O6 m- Z. k) M
    35.         luMessage pMessage;
    36. 4 m, p  W, j1 P* S
    37.         wchar_t wchNum[32];6 E8 _$ `, @7 G\\" q* E& Y
    38.         char chNum[32];: D) ]* ^3 Q& |4 \: [6 Y
    39.         a.BType=luStaData_nil; a.VType=luStaData_nil; a.x=0;0 F0 J9 d7 B6 t+ [  s\\" e
    40.         switch(theOperator)
    41. & \- E; t7 F3 h5 ?: }1 I& ]2 @1 T
    42.         {# H8 F/ |% \, v2 O( j9 j
    43.         case 2:        //重载运算符*% {& P2 @, Q) U. A
    44.                 pRealArray1=(luRealArray *)SearchKey((char *)&(xx->x),sizeof(luVOID),luDynData_realarray);
    45. / Q$ r8 p$ d1 ^$ H/ E
    46.                 pRealArray2=(luRealArray *)SearchKey((char *)&((xx+1)->x),sizeof(luVOID),luDynData_realarray);2 O; l4 F  M3 ^; b9 u  I% m$ M% I
    47.                 if(!pRealArray1 || !pRealArray2) break;        //对象句柄无效,不是实数数组# C$ B7 r* |# i: v  _% ^
    48.                 if(pRealArray1->DimLen!=2 || pRealArray2->DimLen!=2) break;        //不是二维实数数组(矩阵); u. y; Z! {: Y7 X
    49.                 if(pRealArray1->Dim[1]!=pRealArray2->Dim[0]) break;        //维数不匹配& G4 |' v, \5 Q1 {' o7 e5 s2 s
    50.                 pRealArray3=(luRealArray *)NewSysObj(luDynData_realarray,pRealArray1->Dim[0]*pRealArray2->Dim[1],2);        //创建矩阵对象; G4 c# l6 K5 J' j. U5 W. p% Z
    51.                 if(!pRealArray3) break;% L\\" c4 X7 D, R- D% `; d
    52.                 pRealArray3->Dim[0]=pRealArray1->Dim[0]; pRealArray3->Dim[1]=pRealArray2->Dim[1];        //设置矩阵维数大小
    53. . ?6 b' W. b) \5 m- D% {+ o
    54.                 pa=pRealArray1->Array; pb=pRealArray2->Array; pc=pRealArray3->Array;
    55. 4 S- j7 S: @, T' U. w' W
    56.                 m=pRealArray1->Dim[0]; n=pRealArray1->Dim[1]; k=pRealArray2->Dim[1];+ |! [; K' U4 `* z. n( v* q
    57.                 for(i=0; i<m; i++)        //矩阵乘
    58. . e5 n: e+ j\\" n* Q# a7 V- k
    59.                 {
    60. + `9 v0 h% V2 U- @2 r0 ^4 C
    61.                         for(j=0; j<k; j++)
    62. * e5 o! z6 [1 _% j- h$ b
    63.                         {
    64. 3 L: X8 ?' d& l+ I
    65.                                 u=i*k+j; pc[u]=0.0;: p$ E8 \  b* N, P# S
    66.                                 for (v=0; v<n; v++)
    67. 8 R  Z; ~: C, x: A% P7 w4 |\\" D- H
    68.                                 {9 Q: `2 i6 v9 M
    69.                                         pc[u]=pc[u]+pa[i*n+v]*pb[v*k+j];
    70. . N+ y3 c6 X# b, x  o& h
    71.                                 }
    72. / P* o  K: Y, ?
    73.                         }: y# {3 ~4 `( D; _: X
    74.                 }+ E% g/ E+ F0 j) r& A7 W6 ]
    75.                 FunReObj(hFor);        //告诉Lu,返回一个动态对象
    76. & u/ t) h9 w8 |  w: i- b/ ]# G& r
    77.                 a.BType=luDynData_realarray; a.VType=Matrix; a.x=0; *(luVOID *)&(a.x)=(luVOID)pRealArray3;; U6 X+ K1 M8 c5 d\\" r0 N5 I
    78.                 break;7 c3 h( w4 C0 c
    79.         case 25:        //重载运算符.*  |\\" r1 G* g\\" d6 V! R
    80.                 pRealArray1=(luRealArray *)SearchKey((char *)&(xx->x),sizeof(luVOID),luDynData_realarray);) V  S0 X\\" j\\" B; P
    81.                 pRealArray2=(luRealArray *)SearchKey((char *)&((xx+1)->x),sizeof(luVOID),luDynData_realarray);) \: c# @: Q\\" N- Q
    82.                 if(!pRealArray1 || !pRealArray2) break;        //对象句柄无效,不是实数数组
    83. + ~* a7 I: a( T/ r
    84.                 if(pRealArray1->DimLen!=2 || pRealArray2->DimLen!=2) break;        //不是二维实数数组(矩阵)$ H0 g) N, @# t8 J7 Y1 g
    85.                 if(pRealArray1->Dim[0]!=pRealArray2->Dim[0] || pRealArray1->Dim[1]!=pRealArray2->Dim[1]) break;        //维数不相同- D/ B5 L# x# B+ T- [4 M
    86.                 pRealArray3=(luRealArray *)NewSysObj(luDynData_realarray,pRealArray1->ArrayLen,2);        //创建矩阵对象4 \: E. h4 c1 \. _2 m: P% p* P
    87.                 if(!pRealArray3) break;
    88. 7 G! S1 {' [% u
    89.                 pRealArray3->Dim[0]=pRealArray1->Dim[0]; pRealArray3->Dim[1]=pRealArray1->Dim[1];        //设置矩阵维数大小$ B/ J5 ^$ e. E8 c. _) v
    90.                 for(i=0;i<pRealArray1->ArrayLen;i++) pRealArray3->Array[i]=pRealArray1->Array[i]*pRealArray2->Array[i];//矩阵点乘# N: u7 E% W; `& R' a7 L- x# i0 I
    91.                 FunReObj(hFor);        //告诉Lu,返回一个动态对象; s' p2 X# y& }3 B% i# n1 E$ D( o  d8 R
    92.                 a.BType=luDynData_realarray; a.VType=Matrix; a.x=0; *(luVOID *)&(a.x)=(luVOID)pRealArray3;
    93. # l; ^% P2 V8 ^+ y, {. V/ C
    94.                 break;6 z6 Q2 C2 W& q# x% S
    95.         case 46:        //重载函数new  B* |0 f6 t4 |* x\\" Y
    96.                 a=ExeOperator(mm,xx,hFor,theOperator,luDynData_realarray);        //直接调用基本类型luDynData_realarray的new函数
    97. , U' j3 @, f) N! B$ O\\" j# V, L
    98.                 if(a.VType==luDynData_realarray) a.VType=Matrix;        //设置扩展类型为自定义的Matrix类型7 i, O& ~: I0 b$ W6 |% k) i: w+ \
    99.                 break;9 Q9 d0 P& v. E7 s; ~
    100.         case 49:        //重载函数o
    101. 5 i3 n( c! G) K8 p
    102.                 pMessage=(luMessage)SearchKey("\0\0\0\0",sizeof(luVOID),luPubKey_User);5 z. r. a+ v% q  |/ |
    103.                 if(!pMessage) break;
    104. - P+ y* S8 a: D  S4 Z& |
    105.                 pRealArray1=(luRealArray *)SearchKey((char *)&(xx->x),sizeof(luVOID),luDynData_realarray);, X. z4 h$ `7 a. Q' C
    106.                 if(!pRealArray1) break;        //对象句柄无效,不是实数数组
    107. 0 w% u  V# l5 m
    108.                 if(pRealArray1->DimLen!=2) break;        //不是二维实数数组(矩阵)
    109. ! F( q# |: i& N' X
    110.                 pa=pRealArray1->Array;7 C1 u' d5 J% e6 {: B
    111.                 m=pRealArray1->Dim[0]; n=pRealArray1->Dim[1]; k=0;
    112. % m! R7 v2 A  i0 ?8 {4 ^% h
    113.                 for(i=0; i<m; i++)        //输出矩阵2 t/ z5 S8 _! _- d1 ~
    114.                 {3 a- q3 R- s8 {( l! y
    115.                         pMessage(L"\r\n"); k+=2;. y9 q6 A/ U2 S( \8 j+ `7 R2 x
    116.                         for(j=0; j<n; j++)
    117.   n: p$ p* ]. o& U3 x# F. ]
    118.                         {
    119. \\" E6 j: o  x5 a. \; n
    120.                                 _gcvt_s(chNum,pa[i*n+j],16);
    121. 4 }% x8 ~% J9 M4 e, I) Y
    122.                                 for(u=0;chNum[u];u++) {wchNum[u]=chNum[u]; k++;}) j0 X# |: A1 ?9 g) {
    123.                                 wchNum[u]='\0';- l0 ^5 d- ?: p; B
    124.                                 pMessage(wchNum); pMessage(L"  "); k+=2;4 U6 p1 v1 x+ c% E5 P
    125.                         }6 p+ e* ^) Q  L
    126.                 }7 G) I# X' B5 }# I, h
    127.                 pMessage(L"\r\n"); k+=2;2 D+ }3 Z. q+ s# a, d
    128.                 a.BType=luStaData_int64; a.VType=luStaData_int64; a.x=k;        //按函数o的要求,返回输出的字符总数; }' h: l) W, h
    129.                 break;8 a\\" X! f0 }+ x- R
    130.         default:
    131. 3 J& P& [* b4 F+ g: E) F
    132.                 break;
    133. : ^7 m* T: V3 Z  H% B4 p; S$ \% E& }! v
    134.         }' u- A6 k3 P8 v& Z/ u+ M5 L) V& @
    135.         return a;& O5 Y2 k9 J7 ^\\" S, f  `5 h4 W6 c
    136. }
    137. ! s  T+ M+ L3 m3 g, N$ @7 ~
    138. void main(void)9 N' ~7 y$ K) }$ ~# M8 `
    139. {, W5 i; t+ ^$ H  |; U1 f. Y% \
    140.         void *hFor;                //表达式句柄
    141. $ m2 ?8 a* r! t1 e/ G. [. ]# W
    142.         luINT nPara;                //存放表达式的自变量个数- m' C7 X5 R\\" M% w6 u9 Q6 Q+ G
    143.         LuData *pPara;                //存放输入自变量的数组指针$ ^9 O$ w# Q' K% N' U5 U5 \
    144.         luINT ErrBegin,ErrEnd;        //表达式编译出错的初始位置和结束位置, A. y( k0 ^7 C' w% ]. D% P
    145.         int ErrCode;                //错误代码
    146. + `& s( s1 B7 h$ Y- @! k/ l
    147.         void *v;- b& R% B, p: N+ D' e3 r
    148.         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.]}";//字符串表达式,矩阵乘
    149. ! D- U, {2 ^9 [# l
    150.         //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.]}";//字符串表达式,矩阵点乘9 ~8 J* z0 B0 P+ b
    151.         LuData Val;
    152. % r. P: N* B0 C6 c
    153.         if(!InitLu()) return;        //初始化Lu
    154. 3 y\\" [/ F. ~/ ^8 B1 R
    155.         while(LockKey(Matrix,DelMatrix,OpMatrix)){Matrix++;}        //锁定一个键,用于存储矩阵扩展类型' d) H/ }& F0 i/ F\\" C6 @

    156. % R* `! |; W+ \  D1 }
    157.         Val.BType=luStaData_int64; Val.VType=luStaData_int64; Val.x=Matrix;        //定义整数常量, z6 M$ H1 E# f4 |\\" W/ o! H* F
    158.         SetConst(L"matrix",&Val);        //设置整数常量
    159. 1 p8 G1 r  y6 b7 E1 `& |6 K
    160.         InsertKey("\0\0\0\0",4,luPubKey_User,LuMessage,NULL,NULL,1,v); //使Lu运行时可输出函数信息/ z/ o0 K7 k. D: O* Q7 c% U* k
    161.         wcout.imbue(locale("chs"));        //设置输出的locale为中文
    162. , c1 S* e, l$ Q1 N
    163.   
    164.   [0 \3 p1 T- L2 ~5 p1 a; D
    165.         ErrCode=LuCom(ForStr,0,0,0,hFor,nPara,pPara,ErrBegin,ErrEnd); //编译表达式
    166. & Q\\" |0 T4 t6 q% ~, x: P
    167.         if(ErrCode)
    168. 8 ?% V7 ^4 q+ f2 G. ]; R0 w% Z
    169.         {
    170. $ a4 B: k, b5 g2 }* u: k( X
    171.                 wcout<<L"表达式有错误!错误代码:"<<ErrCode<<endl;7 v+ v6 u1 }' S2 h5 f1 U
    172.         }8 E1 D& O  }: W1 a5 ]
    173.         else- x4 |& w* y$ g/ A6 Y& g7 x
    174.         {1 @8 B7 ?( e) \' @5 z
    175.                 LuCal(hFor,pPara);        //计算表达式的值
    176. : \0 [4 o1 p$ j# d; A: D5 v
    177.         }! s3 x6 o7 q, l! e5 J# E4 v
    178.         LockKey(Matrix,NULL,OpMatrix);//解锁键Matrix,本例中,该函数可以不用0 p# O* t8 R! e: \- i
    179.         FreeLu();                        //释放Lu
    180. ) `) {3 M, O8 N6 |; n
    181. }
    习题:
    9 E# j2 d. B% _3 ~" K# [! @# D# g8 P: D$ H
        (1)自定义矩阵的加、减、左除、右除、点左除等运算,自编测试字符串代码,重新编译运行程序,观察计算结果。
    / c3 M: j% \( _) j. m. T  f$ \  N) M4 y8 v
        (2)小矩阵乘效率测试。编译运行以下Lu字符串代码:
    1. main(:a,b,c,d,t,i)=
      & v( \) R0 ?+ O$ H( U- x\" T- @1 p! g
    2.     a=new[matrix,2,2,data:1.,2.,2.,1.],( d2 U: z2 q# J
    3.     b=new[matrix,2,2,data:2.,1.,1.,2.],
      1 c/ {3 a% w6 A# |
    4.     c=new[matrix,2,2,data:2/3.,-1/3.,-1/3.,2/3.],
      $ V+ g) {8 f' A  y& X5 K: V* G
    5.     t=clock(),3 h- ?4 {4 K( F
    6.     d=a*b, i=0, while{i<1000000, d=d*c*b, i++},
      , t8 g% r* `) }1 v( U
    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.
      1 E9 i' y, n1 ~# G
    2. 5. 4.! }% E7 u* c5 C) ~
    3. time=0.875 seconds.
      2 Q# n1 O7 u& F
    4. 请按任意键继续. . .
    复制代码
    Matlab 2009a 代码:
    1. a=[1.,2.;2.,1.];9 ^% B* F& q* x4 Q' e; {- }; ?7 B
    2. b=[2.,1.;1.,2.];& H4 f+ w* h6 `8 @' s7 ?9 r# h- B
    3. c=[2/3.,-1/3.;-1/3.,2/3.];
      0 P4 P0 i. O3 g# a# R) @; e/ s- m. W
    4. tic,
      $ D# U- Q) a7 J: D7 s+ d
    5. d=a*b;
      - m# |+ |# U7 y
    6. for i=1:1000000
      ) E! @0 |9 w$ ]+ Y: \' ~' M( T8 M
    7.     d=d*c*b;
      ) E# E3 V) a# \& ?
    8. end5 m  L3 k/ N+ ~
    9. d,; n. J\" e1 p5 W; P6 l. x5 i# e
    10. toc
    复制代码
    结果:
    1. d =
      . ?# V- @! y$ {! Q
    2.      4     5
      # E% ?# C  B/ H! @% Y
    3.      5     4: z% O3 d) T! Y9 p9 J% d
    4. Elapsed time is 2.903034 seconds.
    复制代码
    本例矩阵乘效率测试,Lu的速度超过了Matlab,主要在于Lu有更高的动态对象管理效率。, x/ [$ A1 \( 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-9-1 16:49 , Processed in 0.391947 second(s), 55 queries .

    回顶部