爱吱声

标题: C++ 提速的新发现 [打印本页]

作者: 雷达    时间: 2022-9-24 22:54
标题: C++ 提速的新发现
C++ 比 Octave 慢好多,怎么破?
, x2 a5 I; g9 R* p6 @4 l8 @) L4 P
  _8 `0 k0 i- R' e* G自相关两层循环,内层循环涉及浮点数计算,试验了一下把内层循环内部全都 comment out 只留个壳子,  但空的内层循环本身就把速度拉下来了,看来问题并不在浮点计算。
! T+ o/ f, s  m! ]# x( w
& o3 d% B! a2 U/ V/ Y速度优化问题真的很有意思啊。6 |7 d0 D( i% k; J, i

- |) w- x7 z: P. E欢迎大家继续讨论
作者: 数值分析    时间: 2022-9-24 23:04
拉下来?拉多少?( o/ k! H5 v! s( e' f
把代码贴上来看看?
  T% Q. T% @2 l1 `7 R. j1 J9 {+ U& S2 t' s
难道分支预测不准破坏流水线执行?不该啊。
作者: 沉宝    时间: 2022-9-24 23:15
会不会代码本身的缺陷阻止了自动优化?另外,硬件配置和开发环境可能也有关系。
作者: 风雨无阻    时间: 2022-9-24 23:33
Maybe Debug mode?
作者: 雷达    时间: 2022-9-24 23:54
本帖最后由 雷达 于 2022-9-24 23:57 编辑
/ ^' e) ^" l' n
数值分析 发表于 2022-9-24 23:04
, I/ B6 e1 F% c5 k+ d拉下来?拉多少?
6 b( d5 v( H" D3 b6 j把代码贴上来看看?
& W1 i% R! T; I7 T$ j8 h& C, w- q1 w
) d2 v/ B3 z6 y8 ?
void xcorr(comp* outcomp, comp* A, int lenA, comp* B, int lenB)
1 o2 L2 F7 O4 r2 \% d" w{9 d0 Q8 T5 y( {
        comp temp, xtimesy;
  J% ]+ O- Q% x        xtimesy.re = 0;
1 C8 H0 N! u6 _! D" @! D        xtimesy.im = 0;# `" `1 S: D; Z- m) @- q4 n
        int j0 = lenB - 1;. ]5 V2 M( R8 L& \3 ?3 H* c7 I; {
        int    i, j, i1, reali;' m4 G. K0 r' B% p/ o: k& C: w* o
        if (lenA % 2 == 1)
( Z' S' L+ r( [/ k) E% K                reali = lenA + 1;9 u1 S+ |$ e, [( d* h6 d
        else4 X  d% z& D6 T+ k
                reali = lenA;
) }/ h  }7 R0 l, v+ G        reali /= 2;
1 o/ e, o% I3 l4 L' R
) @; R! A; ~% {1 |6 {        int nconv = reali + lenB;
! v: M1 `' t+ }0 I6 `        //#pragma omp parallel for% ^. @) k/ D! W
        for (i = reali; i < nconv; i++), `2 r9 A/ T! z: R/ l4 o
        {
" N3 u& `) w( u! T! U' M                temp.re = 0;
5 `- {) n$ C. S" C! I                temp.im = 0;- H: e- P, V( d, ?& x) d+ Z/ X0 R% O
                i1 = i;4 r1 ^4 F, @4 }3 {5 s" M# D8 M
                for (j = j0; j >= 0; j--)9 [1 M0 o- U6 d( L5 Y% G* H$ @) I
                {
1 g0 c# V/ F5 o# H                        /* floating date operation */
5 U( _) Q' ~) D% S, A2 W                }

; x, V& Z8 G/ [3 i$ w% w8 ]% x        }
' m1 r  M4 {! u$ q! Q$ u5 @+ U}' n9 `$ J, I- ~9 p. s6 H
# O/ O& r, I( d* B, o) _* I
xcorr函数代码如上,comp是复数struct, 做过长度为11、19两个矢量的测试,和octave结果完全一样
( m# E) T2 p* A+ ^2 g! k" a* z
) f* q7 s3 D' i' X* M( t- U, @红色部分是内循环,现在其内部操作都comment out 了, j0大概是 6000。
7 v4 {. L9 F% T! A5 T现在call xcorr 100次,耗时78s.
2 n& ^% y! x/ |8 I( I3 E. j
3 t4 C; M# b8 o' @3 R如果把红色部分内循环本身完全comment out, call xcorr 1000次,耗时 <1s.
5 `) [# F% J. d
* P3 @( s# u/ S
作者: 雷达    时间: 2022-9-25 00:17
风雨无阻 发表于 2022-9-24 23:33! s5 r9 f, n$ D0 y
Maybe Debug mode?

  I0 S" @. w! Q, }7 o, ?1 O5 |% v' H4 Q$ l( w0 |
不应该,看我上面的回复。
- g3 `% u3 k' {7 D2 V0 s  i
/ ]" N4 r1 y/ c6 k; y  r9 {. y我更怀疑是 VS 社区版的问题
作者: 数值分析    时间: 2022-9-25 00:20
本帖最后由 数值分析 于 2022-9-25 00:24 编辑
# k$ D* n) u& w1 U
雷达 发表于 2022-9-24 23:54% `; P/ T+ ?: Q1 X4 ?
void xcorr(comp* outcomp, comp* A, int lenA, comp* B, int lenB)
2 b$ t6 R1 w8 K8 V  G2 J( P- i{* U- N6 [# l2 W. X- \  f1 f2 p
        comp temp, xtimesy;
5 S; b6 J0 k) s& K9 i7 C

9 K; Z; Z" G4 U6 o* `+ Y, g2 \这个不是这么比的吧。。。0 L- F- I$ s; G( Q0 ?0 Z+ j; O

) R' Z5 v6 h! V0 D  u您这个函数,不带内循环的话,汇编完总共操作也没几个(不到100个)。
: @% H- w/ K% w- u+ D5 X- }( H0 ?0 x5 I0 g/ t: q
而加上内循环,光jmp和dec指令就至少多执行了6000个,慢个几十倍不是正常的么?
作者: 雷达    时间: 2022-9-25 00:46
本帖最后由 雷达 于 2022-9-25 01:09 编辑
% w3 y# ]4 v! W' z' [* e
数值分析 发表于 2022-9-25 00:208 j- b. j; z$ x" {4 Y
这个不是这么比的吧。。。
" ^) A* p( i# y7 I  k* A+ t; n$ J- _
/ j2 U% N' w5 I5 i您这个函数,不带内循环的话,汇编完总共操作也没几个(不到100个)。

( a3 r6 x' v: g4 U; l& O. I& M6 i$ e7 a  _& X! d6 r: Q2 c1 `
有道理。' p( G! {' J6 v+ z
所以存在内循环速度就上不去,把内循环取消,改成两个向量直接点乘再求和应该就会好得多,记得 numeric 库里有算向量内积的,我回头试试。
/ l9 O# \$ b3 j9 m5 H: P) M' o
9 |# E) d' R6 {. R) i/ I# D! @我先尝试尽量用标准库,一个小程序,不想搞得太复杂。多谢了
作者: 沉宝    时间: 2022-9-25 01:27
雷达 发表于 2022-9-25 00:46
# ^' \9 M9 z" f: g1 v有道理。
" x: w! P2 P' f$ v2 V, q  F, C- U所以存在内循环速度就上不去,把内循环取消,改成两个向量直接点乘再求和应该就会好得多,这大 ...

7 `; g6 G; P) d8 s5 Z% W9 D你两个试验之间就差了一个空循环, call 1000次按理不会有秒级差异,可能还是编译器优化的问题。举个例子,把循环本身翻译成机器指令loop或dec/jnz,两者速度上会差很多3 b8 D! W8 D* _  \( W  G- C+ a
Why is the loop instruction slow? Couldn't Intel have implemented it efficiently?
作者: 沉宝    时间: 2022-9-25 01:48
数值分析 发表于 2022-9-25 00:20
" T1 x. O* A' u0 i这个不是这么比的吧。。。
# c. L% w% S/ L$ U* \. x5 |4 e& r7 [3 d/ A3 ^/ \
您这个函数,不带内循环的话,汇编完总共操作也没几个(不到100个)。
而加上内循环,光jmp和dec指令就至少多执行了6000个

" ?2 e! C" I' h  r, R  n2 a9 h2 z* [/ z9 P5 f& ?
现在的CPU,可以把判断、jmp和dec指令全部融合进一个µOp(微操作,CPU内部流水线上的执行单位)。如果循环这样跑,花不了多少时间。
作者: 数值分析    时间: 2022-9-25 02:06
本帖最后由 数值分析 于 2022-9-25 02:16 编辑
4 N% i- B7 Q1 [- N6 t$ T& @
沉宝 发表于 2022-9-25 01:486 h9 N+ g' |" F; h9 A% V0 y
现在的CPU,可以把判断、jmp和dec指令全部融合进一个µOp(微操作,CPU内部流水线上的执行单位)。如果 ...
. ^8 K$ {& {! T8 Q
) b$ P' Z/ G# d
是的,兄台说的对。
6 @7 Q! H: F7 H1 d5 g6 A! @8 B( `2 {. ^8 G/ B
其实我想说的是 真正数值计算部分和代码中其他不直接计算的overhead的比值这个事儿。+ c" C0 K5 S7 }5 I

! u% ?' w9 R! _+ r雷达兄构造测试用例的时候,屏蔽掉了所有计算的部分,使得剩下的都是overhead,这样run time比较的结果就显得好像不合理了。如果把计算加回去,计算部分的run time会dominate,结果就不那么离谱了。因为不好说,所以用指令数对比的方式试图直观地说明这一点。
4 C' o) x4 N) m! }/ O% q
- T8 `. p* |$ E* u0 R% z& \比如说,如果有计算,那么跑六千个循环相对于计算应该用不了多少时间。但是如果一边是什么都不做,另一边是六千个循环,那六千个循环比什么都不做慢几十倍了,就不是那么不合理了。
( p0 {0 F5 ?7 ~0 _( h7 L& u) j& f; m3 p3 d+ M! {- V6 \* `% g
当然也有可能像兄台说的,是优化参数的问题,但我觉得更多地是测试用例设计的不合理。
作者: 雷达    时间: 2022-9-25 04:47
本帖最后由 雷达 于 2022-9-25 04:49 编辑
( @% I3 d7 K, p5 c
沉宝 发表于 2022-9-25 01:27" a1 p3 ~6 g1 s% y
你两个试验之间就差了一个空循环, call 1000次按理不会有秒级差异,可能还是编译器优化的问题。举个例子 ...
9 R9 `2 J; i6 I& G
' L0 V( e) Y2 ]$ X4 ^4 m# z7 N; S
又写了个小实验,没有调用子函数,双层循环,外层6千次,内循环30万次空转,有或没有空转内循环,时间差一倍,我上面这个差的太多了。9 T/ o9 z6 i& X2 P8 P

4 K% h% V* X0 c" @9 ?- b* O我已经完全懵了。
作者: 沉宝    时间: 2022-9-25 05:51
雷达 发表于 2022-9-25 04:47
: A! |0 p  }, {# R/ e又写了个小实验,没有调用子函数,双层循环,外层6千次,内循环30万次空转,有或没有空转内循环,时间差 ...
* `/ A% d1 I, ]8 w+ s& r  e6 f
时间差一倍的结果可以接受。/ C' A# M' ]8 W' e+ k9 j
+ E4 \4 s0 w3 u1 u2 G
你还是用profile工具看看吧。现在大家都主观瞎猜。
作者: 数值分析    时间: 2022-9-25 14:58
本帖最后由 数值分析 于 2022-9-25 15:38 编辑 5 R# q  r8 [; A; i) x
雷达 发表于 2022-9-25 04:47
* c1 R$ P6 W! u4 l: U) B  B8 s又写了个小实验,没有调用子函数,双层循环,外层6千次,内循环30万次空转,有或没有空转内循环,时间差 ...
0 J. G7 C8 e; U' Q
1 [9 O# m0 l0 X7 }& h' J

* w* D% ?; F" L" i0 e7 t3 @+ {- @/ i& d5 P% b& {
能不能把这个也贴上来,看看和上一个有什么不同?
作者: 雷达    时间: 2022-9-26 01:30
本帖最后由 雷达 于 2022-9-27 01:17 编辑
- W2 E: [  d: k4 ?0 I9 T. U+ P
数值分析 发表于 2022-9-25 14:581 O; Z$ K4 ?  I) X0 h, R8 J* @
能不能把这个也贴上来,看看和上一个有什么不同?
0 t4 F' i( I7 Y& h
理了理思路,重新做了一个测试。$ L  B) r  n* b
做了两个 vector 和 两个 float *, 都长 100000& `' @7 f, l# x; A: r" |6 }6 H: T
外循环 6000,里面先做随机数生成,模拟真实环境,避免数据的 cache.9 u( c: C1 E+ \$ k* \

2 S2 q; ]9 p* q  U$ q内循环试了4种方法,/ d4 J) _% b' D/ Z# s1 f2 u
1. 直接调用 vector inner_product 247s 9 [' B2 C. K- F  r$ `
2. vector 循环点乘累加 237s0 _9 @- L9 c# K  J* n8 Q. y% O
3. float * 循环点乘累加 204s
" X& G4 }& n4 m% {. g9 Y' U4. 空循环 100000 次 202s
7 M+ E, Y9 U6 u# _4 j8 b
* ~# m6 L: z. G: p& j2 g不做内循环 200s: \. S* g4 j6 x2 j

1 M( c" d4 D5 L& R0 Y  G你昨天说的对,内循环本身占比是很小的,大头在其他处理。
8 N2 `. C+ A: o% R/ d3 D另外可以看到, float * 循环点乘累加 并不差,比用vector 还更快。
# H" W7 s& G/ T2 M# w0 [, w6 v* |! t9 S/ `
至于我那个原始程序,还有一些疑问,见5楼,其他都不变仅仅是有无空的内循环就有很大不同,这是不对的,也许有一些其他缺陷我没有看到。(也许可以改成 while 试试)
% \8 [* F) @8 n  C) z
& m0 h& |) u0 f; t(为什么下面我贴的  b1 加 方括号里的 i , 显示出来却是 b1 ?方括号 i 消失了。 LOL . 改成  jj 好了,原来 方括号里的 i 是斜体标志  LOL)- y6 W7 {/ N* r4 B/ P

6 Q, V! k4 z( C$ I
        std::vector < float > vec1(N);
  }8 y& I* ^4 j# Y        std::vector < float > vec2(N);
9 v# }6 U* r" L% T& k( }        float* b1 = new float[N];
* L+ m+ P/ y# Z) p/ B5 G" E        float* b2 = new float[N];
  s' F# q) x" M, |. U) }
; _& j8 i* y+ @$ Z" w        for (int j = 0; j < 6000; j++)
$ T! J" {, ?4 {# E        {7 \& y. u  d" K6 O" \1 p
                std::generate(vec1.begin(), vec1.end(), []() {4 b! y$ r3 Q* [/ V# b  |
                        return static_cast <float> (rand()) / (static_cast <float> (RAND_MAX / 23.23));;" H' R- M4 x' D0 L/ R' n- C
                        });" y- H" u, i6 C7 u$ C6 o

0 u! N: z3 E1 t2 w                std::generate(vec2.begin(), vec2.end(), []() {
1 j2 v( X- Z- Y                        return static_cast <float> (rand()) / (static_cast <float> (RAND_MAX / 24.31));;& r* V7 f: U& N" e
                        });
. X2 f, t- I( {1 S8 N9 h# J. v9 ~1 V4 M* O
                for (size_t jj = 0; jj < vec1.size(); jj++)
; J+ k& G' \* k7 g0 Z                {- y% W& i2 q$ R
                        b1[jj] = vec1[jj];# i2 @- m( i& B
                }# k1 _6 e1 ^) r7 K1 q" Y

* D/ l8 g, P; N) S9 c8 D  @. O+ b                for (size_t jj = 0; jj < vec2.size(); jj++)0 x0 ^/ j: l; h% n8 j, f
                {
- u5 k9 Z) N) R1 M' R2 d                        b2[jj] = vec2[jj];
3 S( H6 c, f2 ~# D( L                }; B$ _3 N: w# P7 b* l  T, [! G2 K
3 b. C" c6 ~6 d& ~0 G9 U/ [# ^
                //Method - 1  N=100000 247s  8 T" R/ N5 j  o% `. l/ i
                //fresult = inner_product(vec1.begin(), vec1.end(), vec2.begin(), 0);: T7 Y7 o) Z$ _5 m' g* N1 R
                                ! E0 _7 H3 p/ O6 g, C- ]$ j3 |
                //Method - 2  N=100000  237s, c+ H7 @1 o2 [! G7 D. k
                /*
3 L, X' K4 J/ o, v8 v! f) G: e                for (int jj = 0; jj < N ; jj++)
& a- R" ]( Y# z  k                {1 q5 Z2 T4 l. j: x
                        fresult += vec1[jj] * vec2[jj];
( h  k6 e5 Q8 l" y( x                }/ ?) J$ i$ o! l( A
                */' J% w% T7 ~! Q5 }4 E4 {- p$ z6 H
                                
2 }( {' c8 H" T                //Method - 3  N=100000 204s& @7 |8 w5 W  _2 f" Z
                /** C: H1 P9 v* _( j1 k4 F% `* v
                for (int jj = 0; jj < N; jj++): _/ i" p8 g1 y" m2 ^8 u: {
                {" a2 {4 L0 N( [2 K- Y
                        fresult += b1[jj] * b2[jj];
/ y, P. X, L1 D+ P; M. \4 y# y                }7 x6 y6 r/ `& T5 \2 ]. C. M
                */. J/ P" g9 a8 H" H1 m+ H" s

* z' [$ ?! M2 ~/ x% N                //Method - 4   202s" n) L. m$ D; m' U2 t
                /*; D, A2 w2 k0 T$ w6 {( S
                for (int jj = 0; jj < N; jj++)
! Q& q+ S$ F% x5 _& c                {5 H5 p' j8 e+ [
                        0 W9 c9 R; k' ^3 y
                }
: u" o& D0 z1 S3 D# v. ~                */
  I$ l& S. O9 n, F' V  W$ R  U                //comment out all methods, N=100000  202s                  u7 `" ^0 v; ~
        }
! X4 j" s' ^6 F6 S6 U0 ?; `2 W' o3 i1 R4 I
        delete []b1;, X% c6 [+ P  Y; U! o% F
        delete []b2;

" F6 W+ T) A- `' C9 e" o
作者: 机器猫    时间: 2022-9-27 00:15
瞎猜一下啊。把第一个的那个j定义成register变量会不会有不同?
4 ?3 \9 c! T- Z( g, [1 ^7 |+ t# F9 T6 t1 l7 }8 Z9 D4 ]/ ]9 G
你第二个试验里面的j在循环里面又重新定义了啊,你确定真的跑了6000次?
" y8 ]) I3 g/ J5 {6 j' @
作者: 雷达    时间: 2022-9-27 01:16
机器猫 发表于 2022-9-27 00:151 G* z1 m( T  ?6 _* `$ E
瞎猜一下啊。把第一个的那个j定义成register变量会不会有不同?
: t# F1 e' m. }+ B
# ^8 |! e7 W$ g1 x2 i你第二个试验里面的j在循环里面又重新定义 ...

# G& s: t! ]. S. u% T% t内循环里面的 j 实际是 i, 为了规避爱坛显示的冲突帖子里临时改成了j, 现在是 jj 了。好累 、LOL! @2 j# l' i. F8 y" R/ e
1 Z* i2 b1 A& ^( _
不和它较劲了,瞎耽误工夫,我已经转到 ubuntu, 也准备顺便试试 avx2 向量化。
作者: 机器猫    时间: 2022-9-27 02:06
雷达 发表于 2022-9-27 01:16  ?: k! c4 T; E4 U6 L
内循环里面的 j 实际是 i, 为了规避爱坛显示的冲突帖子里临时改成了j, 现在是 jj 了。好累 、LOL
; h% S8 |. b0 u6 z) o8 w8 r" n" G- ~8 u5 {5 O! W7 S
不和它 ...

* c- o: f- V" S% A' q- ^; R- l9 k
不过可以试试我说的register变量。前一个试验j是混在一堆其它变量里一起定义的,很有可能是在stack上,这样内存读写会更多,要是再碰上每次都需要加载cache就更慢了。
" R) t8 X. W8 b后面一个是在循环那里定义的,说不定编译器就把它优化成register变量了
作者: opensrc    时间: 2022-9-27 07:25
一个无关问题,为什么爱坛的帖子里在我这里有好些奇怪的东东在里面,是防拷贝措施吗?
作者: 雷声    时间: 2022-9-27 20:29
雷达 发表于 2022-9-24 23:541 p$ r: ]' ]2 y; i
void xcorr(comp* outcomp, comp* A, int lenA, comp* B, int lenB)
9 H, V- F; I# _+ F{
# i2 P; E  f- X0 U        comp temp, xtimesy;

7 `; [& s7 @- H9 N这个code里面如果Openmp没有被注释掉的话,那么temp那个变量应该是定义在循环里面,否则线程之间会存在争夺写入那个temp的风险。9 A. p' D5 m9 u
内层for循环如果没有内部操作的话,编译时应该被优化掉了,和你完全注册掉整个循环是一回事。可能你的编译设置没有打开优化?
/ K% ~3 m# ~! h1 QVS社区版没有问题,我工作用的就是社区版,设置正常的话不会比商业版差。以前游说头头用Intel Compiler,他说不想花钱,而且差不了多少,就一直用到现在。
作者: 雷声    时间: 2022-9-27 20:39
雷达 发表于 2022-9-26 01:30) v+ f9 e% w$ d( Z4 p. n3 v
理了理思路,重新做了一个测试。; P1 e% ^& Y- V8 \1 H* q
做了两个 vector 和 两个 float *, 都长 100000$ f$ u6 z+ _8 U
外循环 6000,里面先做随 ...
( n; G; ~4 d+ `) \/ h/ `' _$ x. R: T
这个时间是从哪里开始算的?
% s6 B2 ?  a! C% c% X  O. b4 k我怀疑这个200多秒里面有200秒花在产生随机数上了,真正计算大概只用了2秒, 用了vector那个因为有vector的额外开销,多了几十秒。. t1 t/ K! J' @4 }
按照两个10万个数字的相关计算的规模来估计的话,两秒都算很长很长了。这个结果真的很奇怪。
作者: 雷达    时间: 2022-9-27 22:41
雷声 发表于 2022-9-27 20:399 a0 ~) c9 r5 q
这个时间是从哪里开始算的?
, ?$ |; V7 ]  B3 `* V! n" C我怀疑这个200多秒里面有200秒花在产生随机数上了,真正计算大概只用了2秒, ...
- V# ~& [% x* R+ @6 Q% S
我不管它了,回头 linux 下换g++重新编译,顺便加上你们建议的向量化。
作者: 四处张望    时间: 2022-9-28 00:12
你这个循环主要的计算时间是那个rand,这个循环本身占用时间微乎其微。
9 a! k4 H, [5 c! Q9 I你的空循环,如果是现在的代码,编译器很可能完全不生成对应代码,因为没有任何输出或者修改变量,所以可以看到时间都是202S。你可以认为啥都不干的时间就是那么多。! r4 W& G; P5 t+ s/ Q# h
与此对应用数组(指针)花了2S
# J7 C) o8 v5 s你用vec1[jj]*vec2[jj]理论上不应该差30多秒,这里很可能是你对vector的操作带来了内存操作,你可以试试把初始化挪出循环然后再比较,理论上vector的随机访问和数组应该几乎没什么区别。
作者: opensrc    时间: 2022-9-28 00:29
雷达 发表于 2022-9-24 23:54* P( C/ Z1 d- `- X1 R! Z: y" l
void xcorr(comp* outcomp, comp* A, int lenA, comp* B, int lenB)
  o' H$ f0 g1 \& l' Z  d{6 _6 P3 R% ~1 D5 D7 N; M& K; A
        comp temp, xtimesy;

" g. Y+ z+ ^+ {8 Y8 p' c% p5 Q4 K我有些迷糊,这样的code,难道不就应该时间差很多吗?也做了个简单的实验,你看看我做的有错吗! Z  h; M0 y# V1 C3 l: [, ]

1 W' m- t3 A5 }! \1 N6 |
作者: 雷达    时间: 2022-9-28 00:49
opensrc 发表于 2022-9-28 00:29' T+ p* Q0 D* R0 e% N4 N9 n- ^
我有些迷糊,这样的code,难道不就应该时间差很多吗?也做了个简单的实验,你看看我做的有错吗
1 R4 I6 x1 L! L1 V9 d: r& O1 Y0 `+ R  g5 v$ E6 S2 [7 p
...

. b, e# o: l$ x2 o, r你是对的,是我搞错了。确实没有优化的情况下,空循环如果次数够长本来就应该耗时较大。我搞错的原因是在不自觉得与 octave 比较,而实际上 octave 是优化过的,和是不是空循环没关系,这种不同条件的比较是没意义的。5 n& B' @. W2 X" Z$ S

; J# Q' P! E0 M  R5 F6 y雷声网友说的也对,空循环应该被编译器优化掉,我的编译器设置有问题。
作者: 雷达    时间: 2022-9-28 00:56
本帖最后由 雷达 于 2022-9-28 01:09 编辑 8 L  z+ z! [2 P! ?' }/ j2 g" f
  Z4 U; Q" p8 s5 {3 O) K1 o7 c3 C
是我自己的理解有误,没有优化的情况下,空循环如果次数够长本来就应该耗时较大。; R' O3 `' o& L2 ]/ [, Y, @
有空时我会试试 SIMD和并行,看看能提高多少。. n1 c+ @( l7 M7 \: B
过去7、8 年没有正经用C++ 写过东西,没有 sense 了 5 O# r/ T6 T4 f
谢谢大家的讨论,I learded a lot.  红包已发  
: E; n3 |9 h! k6 _: Q. G% J( H# ]  I: P1 h
% c, r- S* E/ V9 ]+ X+ |! o0 q

+ c/ ~( i3 r. Q8 X. [' m" _7 \; I$ ^. k! g





欢迎光临 爱吱声 (http://129.226.69.186/bbs/) Powered by Discuz! X3.2