我如何像在C#中一样准确地测量C ++中的某些内容?
这是我的C#代码
var elapsedMilliseconds = (double)(sw.ElapsedTicks * 1000L) / Stopwatch.Frequency;
我正在使用visual studio 2010.
答案 0 :(得分:14)
C#中的Stopwatch类基于这两个Win32 API调用,可以从C / C ++调用:
调用第一个函数并将其除以第二个函数以获得一个以秒为单位的值。
示例:
LARGE_INTEGER freq, start, end;
QueryPerformanceFrequency(&freq);
QueryPerformanceCounter(&start);
// do some long operation here
Sleep(5000);
QueryPerformanceCounter(&end);
// subtract before dividing to improve precision
double durationInSeconds = static_cast<double>(end.QuadPart - start.QuadPart) / freq.QuadPart;
请注意,文档中的以下注释是真实的,应予以考虑。我个人在VirtualBox虚拟机中观察到了这种行为。不同处理器之间可能存在数十毫秒的差异,从而导致意外结果,例如负持续时间和长于预期的持续时间:
在多处理器计算机上,哪个处理器无关紧要 调用。但是,您可以在不同的处理器上获得不同的结果 由于基本输入/输出系统(BIOS)或硬件中的错误 抽象层(HAL)。要指定线程的处理器关联, 使用SetThreadAffinityMask函数。
您可能会对此感兴趣:System.Diagnostics.Stopwatch returns negative numbers in Elapsed... properties
请注意,如果上述两个API不可用或返回失败代码,则Stopwatch类将依赖于GetTickCount。这可能只是为了保持与Windows 9x的兼容性;在现代PC上,我自己没有遇到过这些API的任何问题。但是,GetTickCount不具备您想要的精度。
答案 1 :(得分:1)
我需要更具体的测量并找到一个。谢谢其他答案。他们都很好。有了这个答案,我可以根据需要轻松切换到微秒。
当然,我会接受詹姆斯约翰斯顿作为正确答案的答案,因为有很好的解释和人民的反馈。
全部
int main(int argc, char ** argv)
{
unsigned long long nFreq = GetPerformanceTicksInSecond();
unsigned long long nBefore = GetPerformanceTicks();
timer start1 = timer::start();
CallSomeFunction();
unsigned long long nAfter = GetPerformanceTicks();
const unsigned long long nDiff = nAfter - nBefore;
const unsigned long long nMicroseconds = GetTickMicroseconds(nDiff,nFreq);
cout << "CallSomeFunction() took " << nMicroseconds << " " << time << endl;
return 0;
}
unsigned long long GetPerformanceTicks()
{
LARGE_INTEGER nValue;
::QueryPerformanceCounter(&nValue);
return nValue.QuadPart;
}
unsigned long long GetPerformanceTicksInSecond()
{
LARGE_INTEGER nFreq;
::QueryPerformanceFrequency(&nFreq);
return nFreq.QuadPart;
}
double GetTickSeconds(unsigned long long nTicks,unsigned long long nFreq)
{
return static_cast<double>(nTicks) / static_cast<double>(nFreq);
}
unsigned long long GetTickMilliseconds(unsigned long long nTicks,unsigned long long nFreq)
{
unsigned long long nTicksInMillisecond = nFreq / 1000;
return nTicks / nTicksInMillisecond;
}
unsigned long long GetTickMicroseconds(unsigned long long nTicks,unsigned long long nFreq)
{
unsigned long long nTicksInMicrosecond = nFreq / 1000000;
return nTicks / nTicksInMicrosecond;
}
答案 2 :(得分:0)
检查一下:How to get system time in C++?
你也可以使用GetTickCount: 检索自系统启动以来经过的毫秒数,最多49.7天。
答案 3 :(得分:0)
使用QueryPerformanceFrequency和QueryPerformanceCounter API函数。
LARGE_INTEGER freq;
::QueryPerformanceFrequency(&freq);
LARGE_INTEGER start, end;
::QueryPerformanceCounter(&start);
// do some work
::QueryPerformanceCounter(&end);
double const t = double(end.QuadPart - start.QuadPart) / double(freq.QuadPart);
为了提高准确性,您可能希望减去从结果中调用QueryPerformanceCounter所需的时间。
答案 4 :(得分:0)
Stopwatch-class是QueryPerformanceCounter:
的包装器uint64_t startTime, endTime;
uint64_t frequency;
QueryPerformanceFrequency((LARGE_INTEGER*)&frequency);
QueryPerformanceCounter((LARGE_INTEGER*)&startTime);
//DoStuff
QueryPerformanceCounter((LARGE_INTEGER*)&endTime);
double seconds = (endTime-startTime)/(double) frequency;