clock_gettime()
을 사용하여 코드 조각 (부동 소수점 곱셈)의 시간을 계산하려고합니다. 무작위로 100,000 개의 부동 소수점 10 개 배열을 생성 한 다음 한 번에 10 개를 모두 함께 곱합니다. 내가 원하는 것은 10 개의 부동 소수점 곱셈을 수행하는 데 걸리는 시간을 측정 한 다음 그 시간 값을 총 시간에 더한 다음 끝에 모두 출력하는 것입니다.C에서 clock_gettime을 사용한 타이밍 부동 소수점 계산, 시간이 계속 변경됩니까?
나는 그것이 모두 작동한다고 생각했지만 while 루프에서 내 printf()
문을 제거하면 28125692
에서 17490394
나노초까지 시간이 줄어든다는 것을 발견했습니다! 이것은 일어나서는 안됩니다. 부동 소수점 곱셈의 시작과 끝 부분에서 clock_gettime()
호출을 배치 했으므로 이론적으로 printf()
문이 경과 시간에 영향을 미치지 않아야합니다!
아이디어가 있으십니까? 고맙습니다.
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <time.h>
int main(int argc, char *argv[])
{
int i;
int j;
float alpha[100000];
float bravo[100000];
float charlie[100000];
float delta[100000];
float echo[100000];
float foxtrot[100000];
float golf[100000];
float hotel[100000];
float india[100000];
float juliet[100000];
float max;
long long num_calcs;
struct timespec start_time;
struct timespec end_time;
int diff_seconds;
long diff_nanoseconds;
long long total_calcs;
long long total_seconds;
long long total_nanoseconds;
num_calcs = 100000;
max = 1000.0;
printf("\n%lld floating point calculations requested.", num_calcs);
printf("\nGenerating random floating point values...");
//initialize random seed
srand((unsigned int)time(NULL));
//generate random floating point values
for (i = 0; i < 100000; i++)
{
alpha[i] = ((float) rand())/((float) (RAND_MAX)) * max;
bravo[i] = ((float) rand())/((float) (RAND_MAX)) * max;
charlie[i] = ((float) rand())/((float) (RAND_MAX)) * max;
delta[i] = ((float) rand())/((float) (RAND_MAX)) * max;
echo[i] = ((float) rand())/((float) (RAND_MAX)) * max;
foxtrot[i] = ((float) rand())/((float) (RAND_MAX)) * max;
golf[i] = ((float) rand())/((float) (RAND_MAX)) * max;
hotel[i] = ((float) rand())/((float) (RAND_MAX)) * max;
india[i] = ((float) rand())/((float) (RAND_MAX)) * max;
juliet[i] = ((float) rand())/((float) (RAND_MAX)) * max;
}
printf("done!");
printf("\nRunning %lld floating point multiplications...", num_calcs);
//run calculations
i = 0;
total_calcs = 0;
total_seconds = 0;
total_nanoseconds = 0;
while (total_calcs < num_calcs)
{
printf("\n\nRunning 10 calculations...");
//do 10 multiplications
//start the timer
if (clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &start_time) < 0)
{
printf("\nclock_gettime for start_time failed, exiting...");
return -1;
}
alpha[i] * bravo[i] * charlie[i] * delta[i] * echo[i] *
foxtrot[i] * golf[i] * hotel[i] * india[i] * juliet[i];
//stop the timer
if (clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &end_time) < 0)
{
printf("\nclock_gettime for end_time failed, exiting...");
return -1;
}
printf("done!");
total_calcs = total_calcs + 10; //increase total calculations
i++; //increment array index
//show timing statistics
printf("\nSTART TIME tv_sec: %d", (int) start_time.tv_sec);
printf("\nSTART TIME tv_nsec: %ld", start_time.tv_nsec);
printf("\nEND TIME tv_sec: %d", (int) end_time.tv_sec);
printf("\nEND TIME tv_nsec: %ld", end_time.tv_nsec);
//calculate time it took to run 10 floating point caculcations
if ((end_time.tv_nsec - start_time.tv_nsec) < 0)
{
diff_seconds = end_time.tv_sec - start_time.tv_sec - 1;
diff_nanoseconds = 1000000000 + end_time.tv_nsec - start_time.tv_nsec;
}
else
{
diff_seconds = end_time.tv_sec - start_time.tv_sec;
diff_nanoseconds = end_time.tv_nsec - start_time.tv_nsec;
}
//add elapsed time for the last 10 calculations to total elapsed time
total_seconds = total_seconds + diff_seconds;
total_nanoseconds = total_nanoseconds + diff_nanoseconds;
printf("\nPerformed 10 floating point multiplications in %d seconds and %ld nanoseconds.", diff_seconds, diff_nanoseconds);
printf("\nPerformed %lld floating point multiplications in %lld seconds and %lld nanoseconds.", total_calcs, total_seconds, total_nanoseconds);
}
printf("done!");
printf("\nPerformed %lld floating point multiplications in %lld seconds and %lld nanoseconds.\n", total_calcs, total_seconds, total_nanoseconds);
return 0;
}
'alpha [i] * bravo [i] * charlie [i] * delta [i] * echo [i] * foxtrot [i] * golf [i] * hotel [i] * india [i] * juliet [i];'는 아무 작업도하지 않으며 최적화 컴파일러는 실행 파일에서이를 생략합니다. – pmg
'for '의'printf' 문이 타이밍에 맞지 않는 코드가 성능에 영향을 줄 수있는 데에는 여러 가지 이유가 있습니다. 캐시 미스가 추가로 발생할 가능성이 큽니다. – SJuan76
나노초의 양은 매우 정확합니다. 그것들은 각 구현을 한 번 실행 한 결과입니까? 28 ms와 17 ms 사이의 차이에 대해 이야기 할 때 CPU의 약간 다른 작업량이나 캐시 상태로 인해 쉽게 발생할 수 있습니다. 하나의 구현이 실제로 다른 것보다 느리다는 것을 결정하기 전에 수백 개의 테스트를 실행하고 평균해야합니다. – Daniel