2013-06-19 10 views
9

Ho bisogno di ottenere il tempo di calcolo di alcune parti di un algoritmo che ho implementato in C con NDK/JNI.Come ottenere il tempo di calcolo in ND

ho letto questa domanda: Android Get Current timestamp?

penso di poter ottenere il tempo di calcolo di una chiamata JNI utilizzando lo stesso metodo in questo modo:

Long start, end, time; 
start = System.currentTimeMillis()/1000; 
//my native call 
end = System.currentTimeMillis()/1000; 
time = end - start; 
Log.i(TAG, "Time ... (ms): " + time); 

Ma ho bisogno di controllare il calcolo tempi di alcune piccole parti all'interno del metodo nativo. Come posso farlo?

+0

u puoi farlo impostando i messaggi di log prima e dopo il metodo di chiamata ... e quindi usa solo time = end - start; Voglio dire stampare l'ora nei messaggi di registro. – TheFlash

+0

@AllessandroGaietta il tuo esempio divide 'currentTimeMillis()' per 1000 ... vuoi che la tua misura sia uguale a secondi? – mah

+0

@mah Si tratta di un errore di copia, non voglio dividere per 1000; D –

risposta

7

Da all'interno del vostro codice C/C++,

#include <sys/time.h> 
long long currentTimeInMilliseconds() 
{ 
    struct timeval tv; 
    gettimeofday(&tv, NULL); 
    return ((tv.tv_sec * 1000) + (tv.tv_usec/1000)); 
} 

Questo ti porterà una struttura con l'ora corrente in secondi e microsecondi, dando abbastanza per misurare il tempo tra due punti abbastanza facilmente. Quindi esegue la conversione per restituire l'ora corrente, in millisecondi.

Modifica: aggiornato per @ suggerimento di ChrisStratton.

+0

Questa sarebbe una risposta più completa se mostrassi la conversione dalla struct in un singolo millisecondo o valore di microsecondi in un tipo a 64 bit ... –

+0

@ChrisStratton bel suggerimento; modificato. – mah

+1

Ho un piccolo problema con i tipi aggiungere L ai numeri es. struct timeval stCurrentTime; gettimeofday (& stCurrentTime, nullptr); return ((long long) stCurrentTime.tv_sec * 1000L) + ((long long) stCurrentTime.tv_usec/1000L); // millseconds –

12

È consigliabile non utilizzare gettimeofday() o currentTimeMillis() su un dispositivo mobile. Questi restituiscono l'ora "orologio da muro", che può saltare in avanti o indietro improvvisamente se la rete aggiorna l'ora.

Utilizzare l'orologio monotonico invece per le misurazioni delle prestazioni - System.nanoTime() o clock_gettime() con CLOCK_MONOTONIC. Nota questo restituisce un struct timespec piuttosto che uno struct timeval; la differenza principale è che la risoluzione del clock è in nanosecondi anziché in microsecondi.

int64_t getTimeNsec() { 
    struct timespec now; 
    clock_gettime(CLOCK_MONOTONIC, &now); 
    return (int64_t) now.tv_sec*1000000000LL + now.tv_nsec; 
} 

Oltre all'orario wall-clock si potrebbe essere interessati al tempo CPU per thread; vedi Thread Performance in Android.

+0

Con quale frequenza viene aggiornato l'orario dell'orologio a muro? Ottengo valori temporali molto diversi tra i metodi gettimeofday() e clock_gettime (CLOCK_PROCESS_CPUTIME_ID). Il secondo sembra più stabile, ma il risultato è un tempo più grande del primo, invece mi aspettavo un tempo minore! –

+1

È possibile stabilire con quale frequenza il timer dell'orologio da parete viene aggiornato chiamandolo il più velocemente possibile in un ciclo e sottraendo i risultati la prima volta che il valore cambia. Varia da dispositivo a dispositivo e da rilasciare a rilascio. L'orologio PROCESS_CPUTIME avanza solo quando il tuo processo funziona; se è addormentato, l'orologio non cambia. (Io consiglierei CLOCK_THREAD_CPUTIME_ID per il lavoro sulle prestazioni, poiché avanza solo quando il thread corrente utilizza la CPU.) Gli orologi non sono legati tra loro e non possono iniziare a zero. – fadden

+0

Quello che voglio dire è che misurando con clock_gettime (CLOCK_PROCESS_CPUTIME_ID) (o THREAD, stessi risultati) su un piccolo insieme di operazioni (alcuni millisecondi) ottengo un tempo uguale a gettimeofday() o un semplice clock(). Invece, nei cicli lunghi ottengo un tempo più lungo con il primo, e lo stesso, più breve, tempo con gettimeofday() e clock(). NOTA: in tutti i casi misuro il tempo tra un punto finale e un punto iniziale, il risultato di clock_gettime() viene corretto se la differenza di nanosecondi <0 (secondi ++). clock() è tradotto dividendo per CLOCKS_PER_SEC. –

Problemi correlati