iOS OC内联函数 inline

作者: cyh老崔 | 来源:发表于2016-02-17 16:26 被阅读8040次

inline

在iOS中的一些框架中,static inline是经常出现的关键字组合.

  • static自不用多说,表示在当前文件中应用,如 static A, 在其它文件中也可以出现static A.不会导致重名的错误.
  • inline.内联函数.
  • 作用:替代宏.

(如果你在看框架时,看到inline不解,搜索到这篇文章,看到这里可以不用看下面的详述了)

  • 在框架中出现inline时,如YYKit框架.我们稍加观察就会发现它出现在.h文件中. such as:
static inline CGFloat CGFloatFromPixel(CGFloat value) {
    return value / YYScreenScale();
}

//YYScreenScale()方法说明:
CGFloat YYScreenScale() {
    static CGFloat scale;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        scale = [UIScreen mainScreen].scale;
    });
    return scale;
}

虽然static inline修饰的是函数(或者方法,swift出来后,我觉着方法==函数,朋友们不用咬文嚼字,鄙视我辈了).但它在这里就是宏的作用,即你可以将CGFloatFromPixel当作一个宏.
当然inline函数与宏有区别,inline可以:

  • 解决函数调用效率的问题:
  • 函数之间调用,是内存地址之间的调用,当函数调用完毕之后还会返回原来函数执行的地址。函数调用有时间开销,内联函数就是为了解决这一问题。
  • 不用inline修饰的函数, 汇编时会出现 call 指令.调用call指令就是就需要:
    • (1)将下一条指令的所在地址入栈
    • (2)并将子程序的起始地址送入PC(于是CPU的下一条指令就会转去执行子程序).

结论

为什么inline能取代宏?
  • 优点相比于函数:

    1. inline函数避免了普通函数的,在汇编时必须调用call的缺点:取消了函数的参数压栈,减少了调用的开销,提高效率.所以执行速度确比一般函数的执行速度要快.
  • 2)集成了宏的优点,使用时直接用代码替换(像宏一样);

  • 优点相比于宏:

  • 1)避免了宏的缺点:需要预编译.因为inline内联函数也是函数,不需要预编译.

  • 2)编译器在调用一个内联函数时,会首先检查它的参数的类型,保证调用正确。然后进行一系列的相关检查,就像对待任何一个真正的函数一样。这样就消除了它的隐患和局限性。

  • 3)可以使用所在类的保护成员及私有成员。

inline内联函数的说明
  • 1.内联函数只是我们向编译器提供的申请,编译器不一定采取inline形式调用函数.
  • 2.内联函数不能承载大量的代码.如果内联函数的函数体过大,编译器会自动放弃内联.
  • 3.内联函数内不允许使用循环语句或开关语句.
  • 4.内联函数的定义须在调用之前.

参考资料:

http://stackoverflow.com/questions/11985307/static-extern-and-inline-in-objective-c

http://tigcc.ticalc.org/doc/gnuexts.html#SEC93

相关文章

  • iOS-inline内联函数

    iOS-inline内联函数

  • # iOS OC内联函数 inline

    在iOS中的一些框架中,static inline是经常出现的关键字组合. static自不用多说,表示在当前文件...

  • iOS OC内联函数 inline

    inline 在iOS中的一些框架中,static inline是经常出现的关键字组合. static自不用多说,...

  • iOS OC中内联函数inline

    inline 在iOS中的一些框架中,static inline是经常出现的关键字组合。 static自不用多说,...

  • OC 内联函数 inline

    在iOS的一些框架中, static inline 是经常出现的关键字组合,主要是为了提高函数调用的效率。 内联函...

  • OC 内联函数 inline

    https://www.jianshu.com/p/c838efeb4125?utm_campaign=males...

  • OC(三):内联函数 inline

    inline 一般是和 static 一起使用是将此函数规定在此文件可见,全局的其它文件是无法调用的.而 inli...

  • Kotlin内联函数使用

    inline 本质 Kotlin中的内联函数使用inline关键字修饰,形如: 编译时,inline会将内联函数中...

  • C++ 从入门到放弃 (Day-02)

    内联函数(inline function) ◼ 使用inline修饰函数的声明或者实现,可以使其变成内联函数 建...

  • 内联函数

    内联函数 整理自内联函数百度百科 内联函数是指用inline修饰的函数(并不是所有用inline修饰的函数都是内联...

网友评论

  • moxacist:还有 4.内联函数的定义须在调用之前. 这个是什么意思
    moxacist:@0o低调o0 。。听懂你说的,但是还是不明白第四点为什么要突出说出来
    free如歌:当一个函数是内联和静态的时候,如果所有对函数的调用都集成到调用者中,并且函数的地址从不被使用,那么函数自己的汇编代码就不会被引用。在这种情况下,除非您指定选项“-fkeep-inline-functions”,否则GCC实际上不会为该函数输出汇编代码。由于各种原因,某些调用不能被集成(特别是函数定义之前的调用不能被集成,也不能在定义中递归调用)。如果有一个非集成的调用,那么这个函数就像往常一样编译成汇编代码。如果程序引用它的地址,那么函数也必须照常编译,因为不能内联。
  • moxacist:我自己看了汇编代码,里面有if,依然会汇编成内联函数,还有如果不写inline,编译器会选择性的自动会汇编成内联函数
    cyh老崔:@MoonMD 是的。现在的编译器会自动决定是否内联,可以不用主动inline.
    free如歌:GCC在不进行优化时不内联任何函数,除非您为该函数指定always_inline属性,如下所示:

    / *原型。 * /
    inline void foo(const char *)__attribute __((always_inline));
  • 杰铭的博客:系统的UIKIT_STATIC_INLINE 使用#define来定义static inline的,这样要进行预编译,效率是不是又变低了呢
    cyh老崔:@0o低调o0 兄弟,抱歉不理解你说的内核。验证有没有编译不很简单吗?定义一个错误的宏,查看编译是否报错不就可以了吗?
    free如歌:@崔玉和 这说明什么呢?是不是系统的宏定义直接在内核里了,不用经过启动程序级别的编译。
    cyh老崔:@杰铭的博客 宏是会生成多份内存,但用完就释放。
  • fanglaoda:内联函数内不允许使用循环语句或开关语句.
    麻烦问一下这个是怎么证明的 (换句话说是怎么知道内联函数失效了)
    cyh老崔:@__Ethan__ 准确讲,不是不允许使用。是过于冗长的代码不适合内联。内联的作用就是将函数调用转化成函数体,以节省函数寻址,参数初始化等。如果函数体过长,则编译时间也会相应增加,所以其带来的优势便被抵消。
  • nemie:为什么我看afn的一个inline函数,里面有switch语句啊
    中流者结使也:我也是刚看到
  • 640263ced1b6:“如果你在看框架时,看到inline不解,搜索到这篇文章,看到这里可以不用看下面的详述了”

    太懂我了,不过妥妥的还是应该看完的。
  • 张东帅:碰到这种愿意开源的大牛,简直可以拉升整体水平一大截
    cyh老崔:@XD谢依稀 过奖了,总结了没使用,都他丫的忘了。互相交流,也是普通猿。

本文标题:iOS OC内联函数 inline

本文链接:https://www.haomeiwen.com/subject/bqlmkttx.html