非常实用的Matlab编程技巧。可以试一试。 " ` d C7 S$ ]* t
CTerm下载文章: 紫丁香★
! L, c: V' @' @$ A0 W4 O. t) Z, {6 `1 M1 {+ a, F
发信人: fork (撒哈拉沙漠的沙), 信区: Matlab( @ Y, u9 U& p/ ~% v4 r
标 题: 加速matlab运行的三重境界& i# V1 F/ M* j6 d& n+ i; E
发信站: BBS 哈工大紫丁香站 (Thu Jul 1 14:27:30 2004)- N' \: J2 J6 j3 o o
6 h4 F8 O7 S) M! v加速matlab运行的三重境界& |) m- w$ ?, K. D% e( d* L
一、 遵守Performance Acceleration的规则
' R/ {+ l+ \; A% \! y6 y二、 遵守三条规则6 c5 j3 ?, z3 ?9 K3 v3 V' ?, q
三、 绝招
2 P+ F' W5 K: d- C
一、 遵守Performance Acceleration的规则
3 K; X4 N* P( i5 Z0 [/ A8 F$ N) M2 O, B/ l, t+ T
关于什么是“Performance Acceleration”请参阅matlab的帮助文件。我只简要的将
+ R- s# ?7 n) f8 X其规则总结如下7条:8 w C- g0 S1 r8 |# {
1、只有使用以下数据类型,matlab才会对其加速:0 W8 S* T& [& x- I2 z
logical,char,int8,uint8,int16,uint16,int32,uint32,double
$ A t0 k; p; ?8 \而语句中如果使用了非以上的数据类型则不会加速,如:numeric,cell,structu
5 I/ p2 V/ m; E Zre,single,
: x) e5 o3 D" r/ _/ E, _* Q* }
3 R4 R8 {; [: v1 l; Ifunction handle,java classes,user classes,int64,uint64
" o& D6 F& j" a: o2、matlab不会对超过三维的数组进行加速。6 _$ \/ m" B; [# ~( ? o
3、当使用for循环时,只有遵守以下规则才会被加速:a、for循环的范围只用标量值
9 q# {- l$ o$ R7 G$ g) a9 k1 ~来表示;0 w3 c0 H. L# s2 U4 j0 m
b、for循环内部的每一条语句都要满足上面的两条规则,即只使用支持加速的数: `& U9 b7 K- A: D3 _; T3 o
据类型,只使用
! H @7 x* F' M$ |7 {9 s三维以下的数组;c、循环内只调用了内建函数(build-in function)。
0 M) T9 Z$ {& P3 q# w- P4、当使用if、elseif、while和switch时,其条件测试语句中只使用了标量值时,将& R( q1 L8 b! b0 l1 A( N& O5 d
加速运行。
+ n0 a9 ?7 u6 W L6 m) D3 ]5 ^( P* t+ _5、不要在一行中写入多条操作,这样会减慢运行速度。即不要有这样的语句:" N( n- b+ u# n7 g' G
x = a.name; for k=1:10000, sin(A(k)), end;
+ e7 {8 @4 K0 |9 c4 {* l9 m6、当某条操作改变了原来变量的数据类型或形状(大小,维数)时将会减慢运行速
" S9 {/ z9 s7 o2 W2 O9 n* y7 f) Y- s度。
5 O2 V0 D/ L( ^( M. X7、应该这样使用复常量x = 7 + 2i,而不应该这样使用:x = 7 + 2*i,后者会降低2 V8 W: x5 @ ^- x0 w
运行速度。
& K; D; U8 v8 U0 ~" l* M% Z
- T6 v2 Y" f/ k) G% f+ H, h+ U9 u9 Z3 J' q$ ~! v/ {& @
二、 遵守三条规则
' V+ V) ]3 @7 j6 s) z! e2 r4 |3 r% d6 f/ w
1、尽量避免使用循环,MATLAB的文档中写到“MATLAB is a matrix language, whic
! _8 ]- y2 {1 x( X* Gh means it is designed$ V' p; i& j, O' n$ D' k
4 S B6 ~( m# q4 M
for vector and matrix operations. You can often speed up your M-file c
# `0 W" a5 J8 k Wode by using, x/ q8 |5 L: u; p. a/ R
vectorizing algorithms that take advantage of this design. Vectorizati4 @6 d: Q$ T$ k( i6 A
on means converting
" a& C3 a6 X$ D* T5 [ G1 xfor and while loops to equivalent vector or matrix operations.”。改进1 Y: E/ R# B) o5 t7 V. C8 T
这样的状况有两种方法:/ a& A i5 Z! C4 }' z, {
8 q" H$ a; v: \% W) u4 V7 ]
a、尽量用向量化的运算来代替循环操作。如将下面的程序:
& @ ?* I+ O2 n5 s0 w7 J# n `$ Y, X2 K. X0 V( `, O
i=0;
0 B! K% J$ V2 Zfor t = 0:.01:10* n1 b. a6 P6 |4 e9 L
i = i+1;1 d5 @5 ?! b) A8 D& d, x2 j0 c: O
y(i) = sin(t);
7 T* ?% j3 e6 mend' a/ a3 k& i- `: U" @
替换为:
; ?6 q) \! j) M2 Ft = 0:.01:10;
3 b2 R/ p) j$ j* A- y& c0 Qy = sin(t);
; V: r2 B* l) k J' j速度将会大大加快。最常用的使用vectorizing技术的函数有:All、diff、i, T6 x0 g! ?: L7 i
permute、permute、
, t/ ?9 K: J$ hreshape、squeeze、any、find、logical、prod、shiftdim、sub2ind、cums; F ^( K* L' k/ s) p
um、ind2sub、( T2 a7 l b3 I9 q! @' e; J
ndgrid、repmat、sort、sum 等。 ?7 j7 {6 B" h5 ^/ ?0 e
% g. v& Y" s9 |+ t! ]! ^5 d请注意matlan文档中还有这样一句补充:“Before taking the time to
3 u4 d: i; N; d! v x1 X6 t: E ?
, T9 R, x* P, R+ i/ G% N1 mvectorize your code, read the section on Performance Acceleration.
2 z8 M" F: E( EYou may be able to
* w2 n# ?6 ?& S/ |+ j. espeed up your program by just as much using the MATLAB JIT Accelera- J* W& Q- ~9 _ e/ v" e m, C
tor instead of K" @# r: J }6 V8 C' c
vectorizing.”。何去何从,自己把握。1 G/ {2 g! q; _+ K
1 X% O8 \: v4 _2 E/ M; j: N
b、在必须使用多重循环时下,如果两个循环执行的次数不同,则在循环的外环执
. S1 v0 g( d, ?- n$ d1 j行循环次数少的,
3 p4 E! G [" ^内环执行循环次数多的。这样可以显著提高速度。) g8 q4 [0 A0 t7 G: Q1 [+ [1 z4 ~
- S& ~. o, | ?0 G4 u6 @2、a、预分配矩阵空间,即事先确定变量的大小,维数。这一类的函数有zeros、on
8 C1 S# w; W. |, k$ p' Jes、cell、struct、3 ?# I9 |8 v' n: [
repmat等。 U; L7 x0 H4 U6 s! y+ m0 y, H
b、当要预分配一个非double型变量时使用repmat函数以加速,如将以下代码:) P# ]( P. q, e7 l0 I2 A
& o( a6 T+ c. e" F3 f" b
A = int8(zeros(100));1 R: \; e& v8 C8 k2 ^* [5 r
换成:3 _) l$ {' w4 `' M% \* i0 |3 l
A = repmat(int8(0), 100, 100);* P2 V8 n7 ?1 P! C
c、当需要扩充一个变量的大小、维数时使用repmat函数。- {3 C# t7 e" A3 J$ l% ?- j
1 Z; `/ I$ y% a3 ~# ~
3、a、优先使用matlab内建函数,将耗时的循环编写进MEX-File中以获得加速。
) _. c1 \/ k3 [* M( ib、使用Functions而不是Scripts 。
5 [4 W4 b) T0 {) F, P- x* A% h
3 U( j% j+ E& Z9 q9 B) F
6 _. |8 @, r U; P0 q `: W: Q' a三、 绝招8 U& Q- |6 U! @- B% _0 K( y
* g( K5 W* h o, c, M
你也许觉得下面两条是屁话,但有时候它真的是解决问题的最好方法。# ^5 r0 b/ e3 Y8 v1 T
1、改用更有效的算法
& V. h0 R' P6 p' z! X0 l2 \2、采用Mex技术,或者利用matlab提供的工具将程序转化为C语言、Fortran语言。
$ |" _1 b k1 s5 c9 V+ I) `2 S4 E: I& ~. @$ @8 l
关于如何将M文件转化为C语言程序运行,可以参阅本版帖子:“总结:m文件转化为c/c++9 `+ F; M5 A5 Z1 |
语言文件,VC编译”。 e5 q+ j* R/ Y7 l! i8 P
|