Agora existe um novo método de medição de microssegundos em javascript:
http://gent.ilcore.com/2012/06/better-timer-for-javascript.html
No entanto, no passado, descobri um método bruto de obter precisão de 0,1 milissegundo em JavaScript a partir de um cronômetro de milissegundo. Impossível? Não. Continue lendo:
Estou fazendo alguns experimentos de alta precisão que exigem precisões de cronômetro verificadas automaticamente, e descobri que consegui obter uma precisão de 0,1 milissegundo de maneira confiável com certos navegadores em certos sistemas.
Descobri que, em navegadores modernos com aceleração por GPU em sistemas rápidos (por exemplo, i7 quad core, onde vários núcleos estão ociosos, apenas a janela do navegador) - agora posso confiar que os temporizadores têm precisão de milissegundos. Na verdade, ele se tornou tão preciso em um sistema i7 ocioso que consegui obter com segurança exatamente o mesmo milissegundo, em mais de 1.000 tentativas. Somente quando estou tentando fazer coisas como carregar uma página da web extra, ou outro, a precisão de milissegundos degrada (E eu sou capaz de capturar minha própria precisão degradada fazendo uma verificação de tempo antes e depois, para ver se meu tempo de processamento aumentou repentinamente para 1 ou mais milissegundos - isso me ajuda a invalidar resultados que provavelmente foram afetados de maneira adversa pelas flutuações da CPU).
Tornou-se tão preciso em alguns navegadores acelerados por GPU em sistemas i7 quad-core (quando a janela do navegador é a única janela), que descobri que gostaria de poder acessar um temporizador de precisão de 0,1 ms em JavaScript, já que a precisão é finalmente agora lá em alguns sistemas de navegação de ponta para fazer com que a precisão do cronômetro valha a pena para certos tipos de aplicações de nicho que requerem alta precisão, e onde as aplicações são capazes de verificar se há desvios de precisão.
Obviamente, se você estiver fazendo várias passagens, pode simplesmente executar várias passagens (por exemplo, 10 passagens) e depois dividir por 10 para obter a precisão de 0,1 milissegundo. Esse é um método comum de obter melhor precisão - faça várias passagens e divida o tempo total pelo número de passagens.
NO ENTANTO ... Se eu puder fazer apenas uma única passagem de benchmark de um teste específico devido a uma situação incomumente única, descobri que posso obter 0,1 (e às vezes 0,01 ms) de precisão ao fazer isso:
Inicialização / calibração:
- Execute um loop ocupado para esperar até que o cronômetro aumente para o próximo milissegundo (alinhe o cronômetro com o início do próximo intervalo do milissegundo) Este loop ocupado dura menos de um milissegundo.
- Execute outro loop ocupado para incrementar um contador enquanto espera o incremento do cronômetro. O contador informa quantos incrementos de contador ocorreram em um milissegundo. Este loop ocupado dura um milissegundo completo.
- Repita o procedimento acima, até que os números se tornem ultraestáveis (tempo de carregamento, compilador JIT, etc.). 4. NOTA: A estabilidade do número dá a você a precisão alcançável em um sistema inativo. Você pode calcular a variação, se precisar verificar a precisão. As variações são maiores em alguns navegadores e menores em outros. Maior em sistemas mais rápidos e mais lento em sistemas mais lentos. A consistência também varia. Você pode saber quais navegadores são mais consistentes / precisos do que outros. Sistemas mais lentos e sistemas ocupados levarão a variações maiores entre os passos de inicialização. Isso pode dar a você a oportunidade de exibir uma mensagem de aviso se o navegador não estiver fornecendo precisão suficiente para permitir medições de 0,1 ms ou 0,01 ms. A inclinação do cronômetro pode ser um problema, mas alguns cronômetros de milissegundos inteiros em alguns sistemas aumentam com bastante precisão (bem na hora), o que resultará em valores de calibração muito consistentes nos quais você pode confiar.
- Salve o valor final do contador (ou média das últimas passagens de calibração)
Comparação de uma passagem com precisão abaixo de um milissegundo:
- Execute um loop ocupado para esperar até que o cronômetro aumente para o próximo milissegundo (alinhe o cronômetro com o início do próximo intervalo do milissegundo). Este loop ocupado dura menos de um milissegundo.
- Execute a tarefa que você deseja para comparar com precisão o tempo.
- Verifique o cronômetro. Isso fornece milissegundos inteiros.
- Execute um loop ocupado final para incrementar um contador enquanto espera o incremento do cronômetro. Este loop ocupado dura menos de um milissegundo.
- Divida este valor do contador, pelo valor do contador original da inicialização.
- Agora você tem a parte decimal de milissegundos !!!!!!!!
AVISO: Loops ocupados NÃO são recomendados em navegadores da web, mas, felizmente, esses loops ocupados são executados por menos de 1 milissegundo cada, e são executados apenas algumas vezes.
Variáveis como compilação JIT e flutuações de CPU adicionam imprecisões massivas, mas se você executar várias passagens de inicialização, você terá recompilação dinâmica completa e, eventualmente, o contador se estabiliza em algo muito preciso. Certifique-se de que todos os loops ocupados tenham exatamente a mesma função para todos os casos, para que as diferenças nos loops ocupados não levem a diferenças. Certifique-se de que todas as linhas de código sejam executadas várias vezes antes de começar a confiar nos resultados, para permitir que os compiladores JIT já tenham se estabilizado para uma recompilação dinâmica completa (dynarec).
Na verdade, eu testemunhei uma precisão se aproximando de microssegundos em certos sistemas, mas eu não confiaria ainda. Mas a precisão de 0,1 milissegundo parece funcionar de forma bastante confiável, em um sistema quad-core ocioso onde sou a única página do navegador. Eu cheguei a um caso de teste científico em que eu só podia fazer passagens únicas (devido a variáveis únicas ocorrendo) e precisava cronometrar precisamente cada passagem, em vez de calcular a média de várias passagens repetidas, então é por isso que fiz isso.
Fiz vários pré-passes e passes fictícios (também para liquidar o dynarec), para verificar a confiabilidade da precisão de 0,1ms (permaneceu sólida por vários segundos), então mantive minhas mãos fora do teclado / mouse, enquanto o benchmark ocorria, então fiz vários pós-passes para verificar a confiabilidade da precisão de 0,1 ms (permaneceu sólido novamente). Isso também verifica se coisas como mudanças de estado de energia, ou outras coisas, não ocorreram entre o antes e o depois, interferindo nos resultados. Repita o pré-teste e o pós-teste entre cada passagem de benchmark. Com isso, eu estava quase certo de que os resultados intermediários eram precisos. Não há garantia, é claro, mas mostra que uma precisão precisa de <0,1 ms é possível em alguns casos em um navegador da web.
Este método só é útil em muito, muito nicho casos. Mesmo assim, literalmente não será 100% infinitamente garantível, você pode obter uma precisão bastante confiável e até mesmo uma precisão científica quando combinada com várias camadas de verificações internas e externas.