Explanation wanted: log10 faster than log and log2, but only with O2 and greater
I need to use a logarithm function in some of my code, but the base doesn't matter. So I set out to pick between `log()`, `log2()`, and `log10()` by performance, provided I found any significant differences. (I will refer to said functions as `ln`, `lb`, and `lg` respectively).

*Why am I fussing about this? Because I will be calling the function as often as 400,000,000 times per iteration of an optimisation algorithm. This is neither optional nor the topic of my question.*

I set up some really basic tests, like so:

    timespec start, end;
    double sum = 0, m;

    clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &start);
    for (int n = 1; n < INT_MAX; ++n)
    {
        m = n * 10.1;
        sum += log(m);
    }
    clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &end);

    cout << "ln=";
    cout << diff(start, end).tv_sec << ":" << diff(start, end).tv_nsec << endl;

    ... // likewise for log2 and log10
([timespec diff(timespec start, timespec end)][1] if you so desire....)

The following results were obtained:

    GCC v4.6.3

    -O0
    ln=140:516853107
    lb=155:878100147
    lg=173:534086352

    -O1
    ln=133:948317112
    lb=144:78885393
    lg=163:870021712

    -O2
    ln=9:108117039
    lb=9:134447209
    lg=4:87951676

    -O3
    ln=9:102016996
    lb=9:204672042
    lg=4:153153558

I've looked at the output of compiling with `-S`, but I really don't have a good enough grip on assembler to fully understand the differences. `-S` output: [-O0 -S][2], [-O3 -S][3]


*Why does `lg` optimise better with O2/O3?*

  [1]: http://www.guyrutenberg.com/2007/09/22/profiling-code-using-clock_gettime/
  [2]: http://pastebin.com/u1m5KE1a
  [3]: http://pastebin.com/At3GZEZf
Explanation wanted: log10 faster than log and log2, but only with O2 and greater
===

I need to use a logarithm function in some of my code, but the base doesn't matter. So I set out to pick between `log()`, `log2()`, and `log10()` by performance, provided I found any significant differences. (I will refer to said functions as `ln`, `lb`, and `lg` respectively).

*Why am I fussing about this? Because I will be calling the function as often as 400,000,000 times per iteration of an optimisation algorithm. This is neither optional nor the topic of my question.*

I set up some really basic tests, like so:

    timespec start, end;
    double sum = 0, m;

    clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &start);
    for (int n = 1; n < INT_MAX; ++n)
    {
        m = n * 10.1;
        sum += log(m);
    }
    clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &end);

    cout << "ln=";
    cout << diff(start, end).tv_sec << ":" << diff(start, end).tv_nsec << endl;

    ... // likewise for log2 and log10
([timespec diff(timespec start, timespec end)][1] if you so desire....)

The following results were obtained:

    GCC v4.6.3

    -O0
    ln=140:516853107
    lb=155:878100147
    lg=173:534086352

    -O1
    ln=133:948317112
    lb=144:78885393
    lg=163:870021712

    -O2
    ln=9:108117039
    lb=9:134447209
    lg=4:87951676

    -O3
    ln=9:102016996
    lb=9:204672042
    lg=4:153153558

I've looked at the output of compiling with `-S`, but I really don't have a good enough grip on assembler to fully understand the differences. `-S` output: [-O0 -S][2], [-O3 -S][3]


*Why does `lg` optimise better with O2/O3?*

  [1]: http://www.guyrutenberg.com/2007/09/22/profiling-code-using-clock_gettime/
  [2]: http://pastebin.com/u1m5KE1a
  [3]: http://pastebin.com/At3GZEZf