Fortran rutinas de tiempo intrínsecas, ¿cuál es mejor? cpu_time o system_clock
Cuando sincronizo un programa FORTRAN, generalmente solo uso el comandocall cpu_time(t)
.
ntonces me encontré concall system_clock([count,count_rate,count_max])
que parece hacer lo mismo. Sin embargo, en una mansión más difícil. Mi conocimiento de estos proviene de: Documentación anterior de Intel.
No pude encontrarlo en la página de inicio de Intel. Vea mi marcado a continuación.
Estas son mis preguntas, a continuación le he proporcionado un código para que vea algunos horarios y usos. Me han demostrado que son muy similares en la producción y, por lo tanto, parecen ser similares en la implementación.
Debo señalar que probablemente siempre me quede concpu_time
, y que realmente no necesito horarios más precisos.
En el siguiente código, he tratado de compararlos. (También he intentado cosas más elaboradas, pero no suministraré para mantener la brevedad). Así que básicamente mi resultado es que:
cpu_time
Es más fácil de usar, no necesita las llamadas de inicialización Tiempo directo en una diferencia También debe ser específico del compilador, pero no hay forma de ver la precisión. (la norma es milisegundos) Es la suma del tiempo de hilo. Es decir. no recomendado para ejecuciones paralelas.
system_clock
Necesita preinicialización. Después del proceso, en forma de división. (pequeña cosa, pero sin embargo una diferencia) Es específico del compilador. En mi PC se encontró lo siguiente: Intel 12.0.4 utiliza una tasa de conteo de 10000, debido a la
INTEGER
precisión. gcc-4.4.5 usa 1000, no sé cómo esto diferencia as propenso a encontrarse con wraparounds, es decir, sic1 > c2
, debido acount_max
Es hora de una hora estándar. Por lo tanto, esto generará el tiempo real de un hilo y no la suma.Código
PROGRAM timer
IMPLICIT NONE
REAL :: t1,t2,rate
INTEGER :: c1,c2,cr,cm,i,j,n,s
INTEGER , PARAMETER :: x=20000,y=15000,runs=1000
REAL :: array(x,y),a_diff,diff
! First initialize the system_clock
CALL system_clock(count_rate=cr)
CALL system_clock(count_max=cm)
rate = REAL(cr)
WRITE(*,*) "system_clock rate ",rate
diff = 0.0
a_diff = 0.0
s = 0
DO n = 1 , runs
CALL CPU_TIME(t1)
CALL SYSTEM_CLOCK(c1)
FORALL(i = 1:x,j = 1:y)
array(i,j) = REAL(i)*REAL(j) + 2
END FORALL
CALL CPU_TIME(t2)
CALL SYSTEM_CLOCK(c2)
array(1,1) = array(1,2)
IF ( (c2 - c1)/rate < (t2-t1) ) s = s + 1
diff = (c2 - c1)/rate - (t2-t1) + diff
a_diff = ABS((c2 - c1)/rate - (t2-t1)) + a_diff
END DO
WRITE(*,*) "system_clock : ",(c2 - c1)/rate
WRITE(*,*) "cpu_time : ",(t2-t1)
WRITE(*,*) "sc < ct : ",s,"of",runs
WRITE(*,*) "mean diff : ",diff/runs
WRITE(*,*) "abs mean diff: ",a_diff/runs
END PROGRAM timer
Para completar, aquí doy la salida de mi Intel 12.0.4 y el compilador gcc-4.4.5.
Intel 12.0.4
con-O0
system_clock rate 10000.00
system_clock : 2.389600
cpu_time : 2.384033
sc < ct : 1 of 1000
mean diff : 4.2409324E-03
abs mean diff: 4.2409897E-03
real 42m5.340s
user 41m48.869s
sys 0m12.233s
gcc-4.4.5
con-O0
system_clock rate 1000.0000
system_clock : 1.1849999
cpu_time : 1.1840820
sc < ct : 275 of 1000
mean diff : 2.05709646E-03
abs mean diff: 2.71424348E-03
real 19m45.351s
user 19m42.954s
sys 0m0.348s
Gracias por leer..