如何在C程序中找到某一部分的执行时间?

16

我正在试图找到一种在C语言中获取代码执行时间的方法。我已经尝试了来自time.h的time()和clock(),但是time()返回秒数,clock()似乎给我毫秒(或百分之一秒)的精度,我需要更加精确的时间。是否有一种方法可以以至少微秒级别的精度抓取时间?

这只需要能够在Linux上编译即可。

11个回答

16

您提到了 clock()time() - 您是在寻找 gettimeofday() 吗?

这将填充一个包含秒和微秒的 struct timeval

当然,实际分辨率取决于硬件。


12

说实话,这是一个只有几个宏的东西:

#include <time.h>
clock_t startm, stopm;
#define START if ( (startm = clock()) == -1) {printf("Error calling clock");exit(1);}
#define STOP if ( (stopm = clock()) == -1) {printf("Error calling clock");exit(1);}
#define PRINTTIME printf( "%6.3f seconds used by the processor.", ((double)stopm-startm)/CLOCKS_PER_SEC);

然后只需这样使用:

main() {
  START;
  // Do stuff you want to time
  STOP;
  PRINTTIME;
}

From http://ctips.pbwiki.com/Timer


11

您需要一个性能分析器应用程序。

在stackoverflow和搜索引擎上搜索关键词:linux性能分析。


2
一个分析器提供的是统计信息,这与实际测量并不相同。 - Lee-Man

3

2
尝试使用"bench.h";它允许您在代码中放置START_TIMER和STOP_TIMER("name"),从而可以任意基准测试任何代码部分(注意:仅建议用于短代码部分,不适用于需要数十毫秒或更长时间的操作)。它的精度可以到时钟周期级别,但在一些罕见情况下,它可能会改变中间的代码编译方式,在这种情况下,最好使用分析器(虽然一般来说,分析器对于特定代码部分的使用需要更多的工作量)。
它仅适用于x86。

不错,我们有一个类似的东西,还加了一个有用的功能——PERF_MARK。这个功能可以标记存储在静态数组中的多个点。我们有一个版本,可以保存一个字符串以便更容易地阅读结果,数组默认包含100个条目,但可以更改。PERF_STOP会输出结果。 - Ilya
删除有关多核系统上失败的注释的人:我已经将其删除,因为它是不正确的。该宏自动处理上下文切换和RDTSC值的其他突然变化,因此不存在这样的问题。我在多核机器上专门使用它,它可以正常工作。 - Dark Shikari
Dark Shikari: 这不可能是正确的,这个宏无法处理像抢占式上下文切换这样的事情。它根本不能。它会产生结果,但它们不会准确。此外,它返回的时间是校准到Core2处理器的(由于#define NOP_CYCLES),需要更改以适应其他处理器。 - QAZ

1

你可能想要谷歌一下一个 仪器化 工具。


1

你不会找到一个库调用来让你超越平台的时钟分辨率。可以像其他帖子建议的那样使用分析器(man gprof),或者-快速且简单-在有问题的代码部分周围放置一个循环以执行多次,并使用clock()。


1

gettimeofday()提供了微秒级别的分辨率,而 clock_gettime() 则提供了纳秒级别的分辨率。

int clock_gettime(clockid_t clk_id, struct timespec *tp);

clk_id 标识要使用的时钟。如果您想要一个系统范围内对所有进程可见的时钟,请使用 CLOCK_REALTIME。对于每个进程计时器,请使用 CLOCK_PROCESS_CPUTIME_ID,对于线程特定计时器,请使用 CLOCK_THREAD_CPUTIME_ID


0

这取决于具体情况。性能分析器可以提供全局视图,但如果您需要准确的视图,我的建议是KISS。只需在循环中运行代码,使其需要一分钟左右才能完成。然后根据总运行时间和执行的迭代计算一个简单的平均值。

这种方法可以让您:

  1. 使用低分辨率计时器获得准确的结果。

  2. 避免仪器干扰接近处理器的高速缓存(L2、L1、分支等)问题。但是,在紧密循环中运行相同的代码也可能提供乐观的结果,这些结果可能不反映实际情况。


0

不知道你正在使用哪个环境/操作系统,但如果另一个线程、任务或进程在中间抢占了你的定时代码,那么你的计时可能会不准确。我建议探索诸如互斥锁或信号量等机制,以防止其他线程抢占你的进程。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接