找回密码
 注册
关于网站域名变更的通知
查看: 55|回复: 0
打印 上一主题 下一主题

Linux 程序设计的一些优化措施

[复制链接]
  • TA的每日心情

    2019-11-20 15:16
  • 签到天数: 1 天

    [LV.1]初来乍到

    跳转到指定楼层
    1#
     楼主| 发表于 2024-7-29 16:37 | 只看该作者 |只看大图 回帖奖励 |倒序浏览 |阅读模式

    EDA365欢迎您登录!

    您需要 登录 才可以下载或查看,没有帐号?注册

    x
    本帖最后由 taoyulon 于 2024-7-31 18:00 编辑
      ?6 P0 y3 _9 w; k- n5 r- h" Q" s1 l2 B7 \. b- k: b
    9 m2 h# h2 U5 K) ~3 X3 i( p

    / ^7 g+ a) N5 t; B( Q6 d$ FLinux 程序设计的一些优化措施- @9 X9 B! f2 Q+ F6 _) x
    % X2 x4 A8 v3 x7 \: F5 Z
    这些知识是在平常的阅读中,零散的获得的,自己总结了一下,分享在这里' S. p; l5 u' [

    1 P8 T( _) Y8 C; Y2 d$ c, @6 Y全局变量VS函数参数) K* |  l4 |7 _: i3 A, R. c% K
    0 F5 \6 @, ?* U5 m, b( a: q$ G
    全局变量在Linux下的驱动编程里边,用的是非常多,例如中断服务函数ISR,基本上都可以用全局变量来作为数据的更新,及事件的触发。给函数传递参数的效率一般来说,要低于直接使用全局变量,尤其是参数的数目太多的时候。参数传递,是需要先将参数push到stack中,等程序运行完毕,再从stack中pull出来,过程上要比global variable复杂。但是,全局变量过多的话,这里边就设计到管理的问题了,到后面就很难去控制这些变量的修改,这对于函数的模块化有不利的影响。
    7 n; O3 f4 d, {2 w( r2 y' ^& b$ w3 ]! y$ }/ y! J
    i=i+1;
    5 }) c2 ~/ [) T4 ^4 Si++;! S+ E5 b  C( p6 Y0 R6 _
    i--;! h% N, q# j3 o6 @
    这三个语句都通常引用在for()或者是while()里边,从执行效率上来说 3》2》1
    * ~6 F1 R6 Z8 p  d这和最终生成的汇编语言有关,一般来说,影响不会太夸张。
    / B9 a) W( Y2 r3 W) G
    ! a' P9 N$ Y! d! r$ O$ sswitch-case语句
    * A' w/ A: J. M8 h  t# V
    ) {9 h1 `# U" k/ Hswitch-case语句,也是用的非常多的语句。3 y) Y1 w( x4 T  W4 J1 u$ j2 T
    这里首先的优化原则就是:将发生概率最高的条件,放在最先判断的位置。这样就能够有效的降低
    . K5 |3 e2 K& _5 `/ Q# e1 c! B比较的次数,达到更优的效果。或者,有一种更好的方法来替代switch-case语句的方法,就是利用查表
    $ \% |0 R3 R# x/ M* p比如
    , g  w5 B5 ]. g7 N" m. w# \6 d; Bswitch(msg_type)
    ; `$ C6 i2 l' B{
    ' C- n5 _' g& u' R3 s/ {$ M  J7 mcase DATA:
      E( ?6 Z' ^: J: |  G6 H( x3 \      handle_data_fun();
    1 i0 z7 N' }* V/ s# |8 i2 u      break;
    . z; q+ \: C( `: `5 W5 t7 o+ h( lcase RTS:: k" V9 j, e# e# R( q5 o' L' `
          handle_rts_fun();9 }- W( |0 P5 Z# W3 N
          break; & C) S8 E( F, Z; `6 N
          ........ x6 j5 }9 t; Z0 w+ H0 y! z
    }  
    2 Y3 {4 f. F- c# T这里就可以用函数指针和查表的方式,获得handle_fun的方法来替代。9 z- W) b8 T; {) `" M5 T* ]) }
    2 N  s0 y; @$ d
    处理函数都在初始化的过程中,放到*handle_fun[MAX]相应的位置上* P9 U$ Y! l4 G- a3 ]
    int (*handle_fun[MAX])(struct msg_t *msg);
    4 r" \; a4 L* Q9 }int msg_type = msg->type;+ s/ S$ |, R+ P
    handle_fun[msg_type](msg);//即可; t" X' E) v( o4 U% r8 w
    这种方法,在Linux的网络协议里边,用的非常多,一般对应的查表方式为hash表结构。/ ^! p# v& \, }3 x/ P$ [

    ! ~0 n* e/ W; D& W( v8 b6 psturct  和 union的使用, `$ ~! |, x' z7 n/ W
    " D, d9 V6 ^) Q1 C
    sturcut 使用,一定要考虑到字节对其的问题,struct中,不同的安排顺序,sizeof是不同的所以要调整好位置,尽量保证struct的size最小。; d* j: q4 r" D+ V" e' W1 g3 x

    7 O9 H( V; n4 x! V# t% Junion的使用,比如对不同包的数据结构上,是不一样的,所以尽量使用union来区分不同的包结构这样对程序的可读性比较好。8 n* Y9 Q0 J+ X: P5 V- v: R% w
    # e! |  H$ k6 s
    volatile的使用. P6 Y) P4 E; @* X2 [

    3 i  L+ \7 ]6 f3 i7 v( F' {' l4 F0 V/ q' L这在驱动编程方面是非常有用的一个标志。目的是不让编译器compiler把当前的变量优化掉。尤其是涉及到硬件寄存器的值的时候。
    . d, R2 K# R5 k2 P/ Y! a* R8 c0 U+ S
    乘除运算的简化: f6 u6 }; y# l( u& {" Y

    0 {; ~( t1 ^6 Y6 t6 F乘除运算,对ARM来说太致命,arm的乘除都生成一堆的汇编指令才能完成。所以一般可以通过位操作,比如移位,取低位来进行适当的化简。比如 a*8 = a<<3;
    " z3 ]( K! c; K9 l' c1 n( [/ Z. |# z3 S. `, c' Q' y( W
    Inline 函数
    ' {/ O& y( ^8 `" k在实现比较简单功能的函数,以及那些调用非常平凡的函数,都可以在函数前加入inline的标识。这样在产生汇编的时候,能够更有效。也可以替代较复杂的define语句。
    ) P- ?1 r3 ?( a* t! j1 T  Z
    3 Z( O+ R" t5 p, w' k6 \* |: U
    9 v8 K1 w& ]7 n' e/ x* P$ A/ P4 j; J; V/ c6 u

    9 A, w- F5 w: h: `, H. n9 G& I/ ]0 n- O7 W, [# N' d
    您需要登录后才可以回帖 登录 | 注册

    本版积分规则

    关闭

    推荐内容上一条 /1 下一条

    EDA365公众号

    关于我们|手机版|EDA365电子论坛网 ( 粤ICP备18020198号-1 )

    GMT+8, 2025-8-19 14:33 , Processed in 0.140625 second(s), 26 queries , Gzip On.

    深圳市墨知创新科技有限公司

    地址:深圳市南山区科技生态园2栋A座805 电话:19926409050

    快速回复 返回顶部 返回列表