segunda-feira, 22 de setembro de 2008

Java: Medir tempo de execução de tarefas

Com a necessidade de medir o desempenho de uma determinada classe, criei um cronômetro simples. Acredito que seja um código facilmente encontrado na rede, mas esse é bem optimizado e de fácil utilização.

O cronômetro é uma classe estática chamada Chronometer.java:


/**
* @author J.P. Eiti Kimura Classe para cronometrar
* operações em Java
*/
public final class Chronometer {

private static long startValue;
private static long stopValue;
private static long timeDiff;

/**
* Inicia a contagem temporal
*/
public static void start() {
startValue = System.currentTimeMillis();
stopValue = 0;
timeDiff = 0;
}

/**
* Calcula a diferença temporal
*/
public static void stop() {
stopValue = System.currentTimeMillis();
timeDiff = stopValue - startValue;
}

/**
* Retorna o diferença de tempo medida
* @return tempo em milisegundos
*/
public static long elapsedTime() {
return timeDiff;
}
}


A classe é basicamente formada por métodos estáticos de inicio de contagem de tempo (linha 14), de termino da contagem e cálculo do tempo (linha 23), e por fim, um método que retorna o valor do tempo medido (linha 32).

Para exemplificar a utilização da classe Chronometer, vamos medir o tempo gasto para efetuar duas tarefas usando recursos diferentes.

Imagine uma situação onde se deseja concatenar uma cadeia de caracteres qualquer um número definido de vezes. Qual objeto java seria mais rápido para fazer essa tarefa, um simples String, ou um StringBuffer? Para responder essa questão vamos medir o desempenho com nossa classe de cronômetro.

ChonoTest.java


public class ChronoTest {

public static void main(String[] args) {

StringBuffer sb = new StringBuffer();
String sValue = "";

long time1 = 0;
long time2 = 0;

// mede tempo da primeira operação
Chronometer.start();
for (int i = 0; i < 5000; i++) {
sb.append("It's measure time!");
}
Chronometer.stop();
time1 = Chronometer.elapsedTime();

// mede tempo da segunda operação
Chronometer.start();
for (int i = 0; i < 5000; i++) {
sValue += "It's measure time!";
}
Chronometer.stop();
time2 = Chronometer.elapsedTime();

System.out.println("StringBuffer result:" + time1 + "ms");
System.out.println("String result:" + time2 + "ms");

}
}


Note que inicialmente, utilizou-se a classe de cronômetro para a marcar o tempo gasto para concatenar 5000 vezes a frase "It's measure time!" (linha 12). Após a concatenação, o cronômetro é parado (linha 16) e o tempo é calculado (linha 17).

Executando a classe ChronoTest.java em um computador com processador Core2 Quad, com 2GB de memória RAM obtive o seguinte resultado:

StringBuffer result:16ms
String result:7586ms


Esse pequeno exemplo mostra como é possível calcular o tempo gasto em determinadas operações, pode ser aplicado para verificar o tempo gasto do retorno de um conjunto de dados de um banco de dados por exemplo, e mesmo para identificar qual parte do processamento de uma tarefa é a mais custosa em tempo.

2 comentários:

PabloRS disse...
Este comentário foi removido pelo autor.
PabloRS disse...

Bacana teu código, simples e funcional, vou pegar como idéia e fazer um que retorne em segs.. min ou seja um mais "Human Readable". Show de bola =)