C ++异常,GCC和“内联函数”标志

时间:2010-12-10 20:41:54

标签: c++ optimization gcc exception-handling

我正在阅读有关C ++中异常处理的文章。我在StackOverflow上找到了这个topic。有简单的测试,我改变了一下:

C代码:

#include <stdio.h>
#include <time.h>

#define BIG 10000000000

long f( long n ) {
    long r = 0, i = 0;
    for ( i = 0; i < 1000; i++ ) {
        r += i;
        if ( n == BIG - 1 ) {
                return -1;
        }
    }
    return r;
}

int main() { 
    long i = 0, z = 0;
    for ( i = 0; i < BIG; i++ ) {
        if ( (z = f(i)) == -1 ) { 
                break;
        }
    }
}

C ++代码:

#include <stdio.h>
#include <time.h>

#define BIG 10000000000

long f( long n ) {
    long r = 0, i = 0;
    for ( i = 0; i < 1000; i++ ) {
        r += i;
        if ( n == BIG - 1 ) {
                throw -1;
        }
    }
    return r;
}

int main() { 
    long i = 0, z = 0;
    for ( i = 0; i < BIG; i++ ) {
        try {
         z += f(i); 
        }
        catch(int tmp) {
                break;
        }

         }
}

我用-O2优化选项编译,结果C程序更快:

gcc -O2 kod.c -o prog_c
time ./prog_c

real 0m8.610s
user 0m8.520s
sys  0m0.010s

g++ -O2 kod.cpp -o prog_cpp
time ./prog_cpp 

real 0m25.460s
user 0m25.260s
sys  0m0.020s

size prog_cpp 
   text    data     bss     dec     hex filename
   2019     592      32    2643     a53 prog_cpp

g++ -O2 kod.cpp -o prog_cpp -finline-functions
time ./prog_cpp 

real 0m8.412s
user 0m8.390s
sys  0m0.000s

size prog_cpp 
   text    data     bss     dec     hex filename
   2019     592      32    2643     a53 prog_cpp

输出可执行文件的大小完全相同,但使用-finline-functions程序编译时速度要快得多。我试图调查汇编程序输出,

因为-finline-functions仅在第三级GCC优化中启用,所以它在某种程度上是危险的,所以请告诉我为什么不应该在生产代码中使用它?

我在Intel Core 2 Duo(64位模式)上使用GCC v4.5.2。

1 个答案:

答案 0 :(得分:1)

这些程序并不相同。在C版本中,您将返回您的标记,但在C ++中,您将其丢弃。异常不一定返回给调用者,因此在调用站点和被调用函数中放置一些额外的机器以安排展开堆栈。 C中与C ++异常最接近的是longjmp

当编译器决定执行内联优化时,调用者和被调用者都是已知的,并且异常可以解析为更便宜的分支。

两者都是“安全的”,但是不包含异常的代码比使用异常的代码更小,速度更快是很正常的。