我正在关注这篇文章How to Calculate Execution Time of a Code Snippet in C++,这篇文章给出了一个很好的解决方案,用于计算代码片段的执行时间。但是,当我使用这个解决方案来测量我的代码片段在linux中的执行时间时,我发现我运行程序的所有内容,解决方案给出的执行时间都不同。所以我的问题是如何对执行时间进行客观评估。客观评估对我很重要,因为我使用以下方案来评估同一任务的不同实现:
void main()
{
int64 begin,end;
begin = GetTimeMs64();
execute_my_codes_method1();
end = GetTimeMs64();
std::cout<<"Execution time is "<<end-begin<<std::endl;
}
首先,我运行上面的代码来获取第一个方法的执行时间。之后,我将通过调用execute_my_codes_method2()
来更改上述代码,并获取第二种方法的执行时间。
void main()
{
int64 begin,end;
begin = GetTimeMs64();
execute_my_codes_method2();//execute_my_codes_method1();
end = GetTimeMs64();
std::cout<<"Execution time is "<<end-begin<<std::endl;
}
通过比较不同的执行时间,我希望比较这两种不同实现的效率。
我更改代码并运行不同实现的原因是因为在一个程序中按顺序调用它们非常困难。因此,对于在不同时间运行它的相同程序将导致不同的执行时间意味着使用计算的执行时间比较不同的实现方法是没有意义的。有关这个问题的任何建议?谢谢。
答案 0 :(得分:1)
测量单个呼叫的执行时间对判断任何性能改进毫无用处。有太多因素会影响函数的实际执行时间。如果你是测量时间,你应该多次调用函数测量时间并建立测量执行时间的统计平均值
void main() {
int64 begin = 0, end = 0;
begin = GetTimeMs64();
for (int i = 0; i < 10000; ++i) {
execute_my_codes_method1();
}
end = GetTimeMs64();
std::cout<<"Average execution time is "<< (end - begin) / 10000 << std::endl;
}
此外,除了上面显示的内容之外,预先对你的功能进行单元测试(使用像Google Test这样的体面测试框架)会做出如此快速的判断,因为你提到的更快更容易。
您不仅可以确定运行测试用例的频率(收集统计数据以进行平均时间计算),单元测试还可以证明所需/现有功能和输入/输出一致性未被打破另一种实施方式。
作为额外的好处(正如您提到的那样,顺序运行两个函数时遇到困难),大多数单元测试框架允许使用SetUp()
和TearDown()
方法,这些方法在之前/之后执行运行测试用例。因此,您可以轻松地为每个单个测试用例运行提供一致的谓词或不变条件状态。
作为另一种选择,您可以使用通过代码检测工作的分析工具,而不是自行收集统计数据。一个很好的样本是GCC's gprof。我认为收集的信息是每个基础函数调用的频率以及执行的时间。稍后可以使用该工具分析此数据,以便在您的实施中找到潜在的bottlenecks。
此外, - 如果您决定在将来提供单元测试 - 您可能希望确保您的测试用例能够很好地涵盖有关各种输入数据情况的所有代码路径。关于如何执行此操作的一个非常好的示例是GCC's gcov检测。要分析收集的有关代码覆盖率的信息,您可以使用lcov,这样可以非常精确地全面地显示结果。