0

I'm building a project that compares some methods for singleton in terms of speed.

What I'm trying to do is ask users to input how many times they want to run each method, loop through them, and count CPU tick.

Problem is CPU thick is all 0. What should I do?

Here's my code:

int numOfCalls;
cout << "How many calls do you want for each?";
cin >> numOfCalls;
clock_t beg, end;
beg = clock();
for (size_t i = 0; i != numOfCalls; i++)
    Object* p = GofFixed::instance_GofFixed();
end = clock();
cout << (beg-end) / CLOCKS_PER_SEC << endl;
beg = clock();
for (size_t i = 0; i != numOfCalls; i++)
    Boost::instance_Boost();
end = clock();
cout << (beg - end) / CLOCKS_PER_SEC << endl;
PHG
  • 170
  • 1
  • 12
  • 2
    1) `clock()` provides some measure of processor time, but probably doesn't represent "CPU ticks" 2) the `clock_t` type and `CLOCKS_PER_SECOND` might be integer types, so your division expression is likely truncating 3) your benchmark is quite simplistic, so it might be subject to an optimizer eliding many or all of the loop iterations. – Michael Burr May 28 '15 at 00:36
  • 1
    The default clock tick can be huge, Windows had a fixation on 1/64 ticks per second, so the first think you need to know is how big your system's tick is. If it's Old Windows' 15.625 ms, you may have to run millions of iterations of your program on a 2 GHz PC to see even 1 tick. See: http://stackoverflow.com/questions/12244153/behaviour-of-clocks-per-sec-in-different-operating-systems – user4581301 May 28 '15 at 00:36
  • 1
    Check the resulting assembly, your compiler may have eliminated the `for` loop entirely since you never do anything with it or the results. – Alejandro May 28 '15 at 00:36
  • [Here](http://goo.gl/Z31qJA) is the assembly generated for gcc 4.9.2 no optimization, and [Here](http://goo.gl/DcEHpM) compiled with -O2. Pay attention to `main:` . The optimized build doesn't even reach the for loops (I did change the functions up a bit, since I don't have access to `GofFixed::`), but the idea is the same. – Alejandro May 28 '15 at 00:48
  • What I'm trying to do is count how long they take to run each methods whatever times a user inputs. So, is there the simplest way to do that? – PHG May 28 '15 at 01:12

1 Answers1

3

It is allowed for clock_t to be an integer type by the standard. If it is, then it is subject to integer division rules. It looks like your benchmark will probably run in less than a second. If it does, then (beg - end) / CLOCKS_PER_SECOND will produce a result that is less than 1, which will then be truncated to 0.

A better way to time would be to use std::chrono::high_resolution_clock. You could then convert to any time unit supported by the standard library. It would be better to use a smaller time unit so that sub-second measurements are kept. Using chrono would change your code to this:

auto beg = std::chrono::high_resolution_clock::now();
for (size_t i = 0; i != numOfCalls; i++)
    Object* p = GofFixed::instance_GofFixed();
auto end = std::chrono::high_resolution_clock::now();
cout << std::chrono::duration_cast<std::chrono::milliseconds>(end - beg).count() << endl;
                                           //   ^^^^^^^^^^^^ Used milliseconds instead
                                           //                for greater accuracy

Which should work if the benchmark is not optimised out or does not take less than a millisecond.

You can read more on std::chrono::high_resolution_clock here and std::chrono::duration_cast here.

phantom
  • 3,292
  • 13
  • 21
  • 1
    Bit late, but i guess this should be "end - beg" to give positive duration. If one is interested in CPU Ticks (aka CPI Cycles), here is the right answer via asm "rdtsc": https://stackoverflow.com/questions/13772567/how-to-get-the-cpu-cycle-count-in-x86-64-from-c – IUnknown Nov 15 '22 at 22:58