Читая книгу Андрея Акиньшина “Профессиональный бенчмарк” решил проверять приводимые в книге примеры на практике (автор сам так рекомендует). Начал, конечно же, со столь любимого мною в прошлом “бенчмарка новичков”: измерения DateTime.Now
до и после испытуемого на скорость кода и последующего вычисления разности.
Но вот в чем засада по словам автора: для Windows10
частота обновления DateTime по умолчанию 64Гц. А это значит, что новое значение получается с интервалами 15,625 мс и это же значение составляет точность подхода с DateTime. Т.е для всех операций, которые выполнятся быстрее 15,625 мс мы получим значение времени выполнения интересующего кода равное 0, либо, если не повезёт, то 15,625 мс. Такая точность не всегда бывает недопустима, особенно если испытуемый на скорость код выполняется быстрее.
1 | var list = Enumerable.Range(0, 10000).ToList(); |
Пробую код из книги на Windows10
C#6.0 и получаю результаты около 4,5 мс. Предсказанный Андреем 0 никак получить не удалось, как и собственно 15,625 мс.
Двигаемся дальше.
По словам автора, лучшей альтернативой DateTime.Now
является класс System.Diagnostics.Stopwatch
. Типичное разрешение Stopwatch в Windows10
составляет величину порядка 300-500 нс.
1 | var list = Enumerable.Range(0, 10000).ToList(); |
Этот код на машине автора выдавал результат в 0,05 мс. Однако на моей машине средний результат крутился в районе 0,491 мс, что в 10 раз больше, чем ожидалось!
Никакого анализа причин этих цифр пока привести не могу. Только начинаю погружаться в тонкости бенчмарка. Однако отмечу, что поведение DateTime.Now
на моей машине много точнее, чем на машине автора, а System.Diagnostics.Stopwatch
на моей машине на порядок хуже, чем на машине автора. В целом нужно согласиться с автором, что Stopwatch
точнее (в моей случае на порядок), чем DateTime.Now
.
Также следует иметь ввиду, что кроме низкого разрешения DateTime.Now работает медленнее DateTime.UtcNow, т.к. он пересчитывает часовые пояса. Соглашусь с советом Андрея Акиньшина, что в 99% случаев следует выбирать Stopwatch, а не DateTime. DateTime может потребоваться только в случае, если вам действительно нужно знать текущее время. Если реальное время не требуется, то используйте Stopwatch.