C程序的执行时间

问题描述 投票:181回答:14

我有一个C程序,旨在在几个处理器上并行运行。我需要能够记录执行时间(可能是1秒到几分钟)。我已经搜索了答案,但他们似乎都建议使用clock()函数,然后计算程序所用的时钟数除以Clocks_per_second值。

我不确定如何计算Clocks_per_second值?

在Java中,我只是在执行之前和之后以毫秒为单位。

C中有类似的东西吗?我看过了,但我似乎无法找到比第二种解决方案更好的方法。

我也知道分析器是一个选项,但我希望自己实现一个计时器。

谢谢

c benchmarking
14个回答
306
投票

CLOCKS_PER_SEC是在<time.h>宣布的常数。要获取C应用程序中任务使用的CPU时间,请使用:

clock_t begin = clock();

/* here, do your time-consuming job */

clock_t end = clock();
double time_spent = (double)(end - begin) / CLOCKS_PER_SEC;

请注意,这会将时间作为浮点类型返回。这可能比一秒钟更精确(例如,您测量4.52秒)。精度取决于架构;在现代系统上你很容易获得10毫秒或更低,但在较旧的Windows机器上(从Win98时代)它接近60毫秒。

clock()是标准C;它“无处不在”。有类似系统的功能,例如类Unix系统上的getrusage()

Java的System.currentTimeMillis()并没有衡量同样的事情。它是一个“挂钟”:它可以帮助您测量程序执行所花费的时间,但它并不能告诉您使用了多少CPU时间。在多任务系统(即所有这些系统)上,这些可以是广泛不同的。


3
投票

(如果您的系统管理员更改系统时间,或者您的时区有不同的冬季和夏季时间,那么这里的所有答案都缺乏。因此...)

在Linux上使用:clock_gettime(CLOCK_MONOTONIC_RAW, &time_variable);如果系统管理员改变了时间,或者你生活在一个冬季时间与夏季时间不同的国家,它不受影响。

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

#include <unistd.h> /* for sleep() */

int main() {
    struct timespec begin, end;
    clock_gettime(CLOCK_MONOTONIC_RAW, &begin);

    sleep(1);      // waste some time

    clock_gettime(CLOCK_MONOTONIC_RAW, &end);

    printf ("Total time = %f seconds\n",
            (end.tv_nsec - begin.tv_nsec) / 1000000000.0 +
            (end.tv_sec  - begin.tv_sec));

}

man clock_gettime说:

CLOCK_MONOTONIC
              Clock  that  cannot  be set and represents monotonic time since some unspecified starting point.  This clock is not affected by discontinuous jumps in the system time
              (e.g., if the system administrator manually changes the clock), but is affected by the incremental adjustments performed by adjtime(3) and NTP.

2
投票

每个解决方案都不适用于我的系统。

我可以使用

#include <time.h>

double difftime(time_t time1, time_t time0);

2
投票
    #include<time.h>
    #include<stdio.h>
    int main(){
clock_t begin=clock();

    int i;
for(i=0;i<100000;i++){
printf("%d",i);

}
clock_t end=clock();
printf("Time taken:%lf",(double)(end-begin)/CLOCKS_PER_SEC);
}

这个程序将像魅力一样工作。


-1
投票

有些人可能会发现另一种有用的输入:我使用这种测量时间的方法作为使用NVidia CUDA(course description)进行GPGPU编程的大学课程的一部分。它结合了早期帖子中看到的方法,我只是发布它,因为要求赋予它可信度:

unsigned long int elapsed;
struct timeval t_start, t_end, t_diff;
gettimeofday(&t_start, NULL);

// perform computations ...

gettimeofday(&t_end, NULL);
timeval_subtract(&t_diff, &t_end, &t_start);
elapsed = (t_diff.tv_sec*1e6 + t_diff.tv_usec);
printf("GPU version runs in: %lu microsecs\n", elapsed);

我想你可以乘以1.0 / 1000.0获得适合您需求的测量单位。


-2
投票

冒泡排序和选择排序的执行时间的比较我有一个程序,它比较冒泡排序和选择排序的执行时间。要找出执行代码块的时间,请计算块之前和之后的时间

 clock_t start=clock();
 …
 clock_t end=clock();
 CLOCKS_PER_SEC is constant in time.h library

示例代码:

#include <stdio.h>
#include <stdlib.h>
#include <time.h>
int main()
{
   int a[10000],i,j,min,temp;
   for(i=0;i<10000;i++)
   {
      a[i]=rand()%10000;
   }
   //The bubble Sort
   clock_t start,end;
   start=clock();
   for(i=0;i<10000;i++)
   {
     for(j=i+1;j<10000;j++)
     {
       if(a[i]>a[j])
       {
         int temp=a[i];
         a[i]=a[j];
         a[j]=temp;
       }
     }
   }
   end=clock();
   double extime=(double) (end-start)/CLOCKS_PER_SEC;
   printf("\n\tExecution time for the bubble sort is %f seconds\n ",extime);

   for(i=0;i<10000;i++)
   {
     a[i]=rand()%10000;
   }
   clock_t start1,end1;
   start1=clock();
   // The Selection Sort
   for(i=0;i<10000;i++)
   {
     min=i;
     for(j=i+1;j<10000;j++)
     {
       if(a[min]>a[j])
       {
         min=j;
       }
     }
     temp=a[min];
     a[min]=a[i];
     a[i]=temp;
   }
   end1=clock();
   double extime1=(double) (end1-start1)/CLOCKS_PER_SEC;
   printf("\n");
   printf("\tExecution time for the selection sort is %f seconds\n\n", extime1);
   if(extime1<extime)
     printf("\tSelection sort is faster than Bubble sort by %f seconds\n\n", extime - extime1);
   else if(extime1>extime)
     printf("\tBubble sort is faster than Selection sort by %f seconds\n\n", extime1 - extime);
   else
     printf("\tBoth algorithms have the same execution time\n\n");
}

106
投票

如果您使用Unix shell运行,则可以使用time命令。

$ time ./a.out

假设a.out,因为可执行文件将给你运行它的时间


57
投票

你在功能上想要这个:

#include <sys/time.h>

struct timeval  tv1, tv2;
gettimeofday(&tv1, NULL);
/* stuff to do! */
gettimeofday(&tv2, NULL);

printf ("Total time = %f seconds\n",
         (double) (tv2.tv_usec - tv1.tv_usec) / 1000000 +
         (double) (tv2.tv_sec - tv1.tv_sec));

请注意,这是以微秒为单位,而不仅仅是秒。


54
投票

在普通香草C:

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

int main()
{
    clock_t tic = clock();

    my_expensive_function_which_can_spawn_threads();

    clock_t toc = clock();

    printf("Elapsed: %f seconds\n", (double)(toc - tic) / CLOCKS_PER_SEC);

    return 0;
}

12
投票

大多数简单程序的计算时间以毫秒为单位。所以,我想,你会发现这很有用。

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

int main(){
    clock_t start = clock();
    // Execuatable code
    clock_t stop = clock();
    double elapsed = (double)(stop - start) * 1000.0 / CLOCKS_PER_SEC;
    printf("Time elapsed in ms: %f", elapsed);
}

如果你想计算整个程序的运行时并且你在Unix系统上,那么使用像time这样的time ./a.out命令运行程序


9
投票

很多答案都建议clock()然后来自CLOCKS_PER_SECtime.h。这可能是一个坏主意,因为这是我的/bits/time.h文件所说的:

/* ISO/IEC 9899:1990 7.12.1: <time.h>
The macro `CLOCKS_PER_SEC' is the number per second of the value
returned by the `clock' function. */
/* CAE XSH, Issue 4, Version 2: <time.h>
The value of CLOCKS_PER_SEC is required to be 1 million on all
XSI-conformant systems. */
#  define CLOCKS_PER_SEC  1000000l

#  if !defined __STRICT_ANSI__ && !defined __USE_XOPEN2K
/* Even though CLOCKS_PER_SEC has such a strange value CLK_TCK
presents the real value for clock ticks per second for the system.  */
#   include <bits/types.h>
extern long int __sysconf (int);
#   define CLK_TCK ((__clock_t) __sysconf (2))  /* 2 is _SC_CLK_TCK */
#  endif

因此,CLOCKS_PER_SEC可能被定义为1000000,具体取决于您用于编译的选项,因此它似乎不是一个好的解决方案。


8
投票

Thomas Pornin作为宏的答案:

#define TICK(X) clock_t X = clock()
#define TOCK(X) printf("time %s: %g sec.\n", (#X), (double)(clock() - (X)) / CLOCKS_PER_SEC)

像这样使用它:

TICK(TIME_A);
functionA();
TOCK(TIME_A);

TICK(TIME_B);
functionB();
TOCK(TIME_B);

输出:

time TIME_A: 0.001652 sec.
time TIME_B: 0.004028 sec.

4
投票

您必须考虑到,测量程序执行所需的时间在很大程度上取决于机器在该特定时刻的负载。

知道了,在C中获取当前时间的方式可以通过不同方式实现,更简单的方法是:

#include <time.h>

#define CPU_TIME (getrusage(RUSAGE_SELF,&ruse), ruse.ru_utime.tv_sec + \
  ruse.ru_stime.tv_sec + 1e-6 * \
  (ruse.ru_utime.tv_usec + ruse.ru_stime.tv_usec))

int main(void) {
    time_t start, end;
    double first, second;

    // Save user and CPU start time
    time(&start);
    first = CPU_TIME;

    // Perform operations
    ...

    // Save end time
    time(&end);
    second = CPU_TIME;

    printf("cpu  : %.2f secs\n", second - first); 
    printf("user : %d secs\n", (int)(end - start));
}

希望能帮助到你。

问候!


3
投票

ANSI C仅指定第二个精确时间函数。但是,如果您在POSIX环境中运行,则可以使用gettimeofday()函数,该函数提供自UNIX Epoch以来经过的微秒分辨率。

作为旁注,我不推荐使用clock(),因为它在很多(如果不是全部?)系统上实现得很糟糕而且不准确,除了它只是指你的程序在CPU上花了多长时间。不是程序的总寿命,根据你的问题,我认为你想测量。

© www.soinside.com 2019 - 2024. All rights reserved.