2017-11-06 2 views
-1

Ich bin sicher, die Antwort ist einfach, aber ich verstehe es nicht ganz. Ich versuche, das Delta zwischen zwei struct timespec mit diesem Code zu berechnen:Subtraktion von Long in C verliert an Präzision?

struct timespec start, finish, diff; 
int ndiff; 

/* Structs are filled somewhere else */ 

diff.tv_sec = finish.tv_sec - start.tv_sec; 
ndiff = finish.tv_nsec - start.tv_nsec; 
if (ndiff < 0) { 
    diff.tv_sec--; 
    ndiff = 1L - ndiff; 
} 
diff.tv_nsec = ndiff; 

printf("Elapsed time: %ld.%ld seconds.\n", diff.tv_sec, diff.tv_nsec); 

jedoch der Ausgang ist immer so etwas wie Elapsed time: 0.300876000 seconds. das scheint darauf hinzudeuten, dass ich die letzten drei Ziffern der ns bin zu verlieren (da diese sollte nicht immer Null sein). Kann jemand darauf hinweisen, was das verursacht?

+3

Es gibt keine Garantie, dass eine Zeitangabe nanosekundengenau ist. – rici

+4

'ndiff = 1L - ndiff;' sieht für mich falsch aus. –

+0

... oder vielleicht wäre es genauer zu sagen, dass die Systemschnittstellen, mit denen Sie * eine "struct timespec" * füllen können, nicht garantiert eine Auflösung im Nanosekundenbereich bieten. –

Antwort

2

Verstrichene Zeit: 0.300876000 Sekunden. was darauf hindeutet, dass ich die letzten drei Ziffern der Nanosekunden verliere (da diese nicht immer Null sein sollten). Kann jemand darauf hinweisen, was das verursacht?

Der Code der Uhr berichtete Genauigkeit beträgt 1000 ns. @John Bollinger@rici

und/oder

diff.tv_sec ist nicht unbedingt ein long. Verwenden Sie einen passenden Spezifizierer.

// printf("Elapsed time: %ld.%ld seconds.\n", diff.tv_sec, diff.tv_nsec); 
// Also insure fraction is printed with 9 digits 
printf("Elapsed time: %lld.%09ld seconds.\n", (long long) diff.tv_sec, diff.tv_nsec); 

Auch falsch "borgen" math wenn die ndiff aktualisieren.

ndiff = finish.tv_nsec - start.tv_nsec; 
if (ndiff < 0) { 
    diff.tv_sec--; 
    // ndiff = 1L - ndiff; 
    ndiff += 1000000000; 
} 

Noch besser, lassen Sie die int diff Variable fallen.

diff.tv_sec = finish.tv_sec - start.tv_sec; 
diff.tv_nsec = finish.tv_nsec - start.tv_nsec; 
if (diff.tv_nsec < 0) { 
    diff.tv_sec--; 
    diff.tv_nsec += 1000000000; 
} 

Sollte finish auftreten, bevor start, dann einen anderen Code können die 2 Mitglieder von diff mit dem gleichen Vorzeichen zu halten wünschen übrig.

+0

Das gibt das gleiche Ergebnis. – user8793

Verwandte Themen