Какова максимальная точность таймера в .NET?

Мне интересно, какова точность класса Timer в System.Timers, потому что это двойное число (что, казалось бы, указывает на то, что у вас могут быть доли миллисекунд). Что это?


person RCIX    schedule 02.10.2009    source источник


Ответы (6)


Настольные ОС Windows действительно не точны ниже 40 мс. ОС просто не работает в режиме реального времени и поэтому имеет значительный недетерминированный джиттер. Это означает, что, хотя он может сообщать значения с точностью до миллисекунды или даже меньше, вы не можете рассчитывать на то, что эти значения будут действительно значимыми. Таким образом, даже если для интервала таймера установлено значение менее миллисекунды, вы не можете полагаться на то, что время между установкой и срабатыванием действительно будет таким, как вы сказали.

Добавьте к этому тот факт, что вся структура, в которой вы работаете, является недетерминированной (GC может приостановить вас и выполнить сбор в течение времени, когда должен срабатывать таймер), и вы в конечном итоге получите массу и массу риска, пытаясь сделать что-либо, что является критичным по времени.

person ctacke    schedule 02.10.2009
comment
Это не особенно критично; Я пишу виртуальный процессор для игры-симулятора роботов, который использует таймер для выполнения инструкций с заданной скоростью, и мне просто интересно, насколько высоко я могу его установить. - person RCIX; 03.10.2009
comment
Я бы не стал пытаться делать это чаще, чем 1 мс. В любом случае планировщик ОС не будет делать ничего более частого, чем это для вашего приложения. - person ctacke; 03.10.2009

System.Timers.Timer странный. Он использует двойной интервал в качестве интервала, но на самом деле вызывает для него Math.Ceiling и приводит результат к типу int для использования с базовым System.Threading.Timer. Его теоретическая точность составляет 1 мс, и вы не можете указать интервал, превышающий 2 147 483 647 мс. Учитывая эту информацию, я действительно не знаю, почему в качестве параметра интервала используется двойное число.

person Julien Lebosquain    schedule 02.10.2009

Пару лет назад я обнаружил, что точность составляет около 16 мс... но, к сожалению, я не помню подробностей.

person crander    schedule 03.10.2009
comment
Это будет 15,625 мс == 64 Гц, частота системных часов. - person Matt Howells; 14.09.2011

Вы можете легко убедиться в этом самостоятельно, выполнив цикл, который постоянно сэмплирует результирующую продолжительность времени и проверяет, с какой степенью детализации он проходит.

person shoosh    schedule 03.10.2009

Я сравнил System.Timers.Timer и System.Threading.Timer - оба дают систематические ошибки в районе 8..16 мс, особенно на малых интервалах (1000..6000 мс). Каждый последующий вызов подпрограммы таймера происходил с увеличенным интервалом от первого вызова. Например, таймер с интервалом 2000 мс срабатывает через 2000, 4012, 6024, 8036, 10048 миллисекунд и т. д. (Временные метки, полученные из Environment.TickCount и Stopwatch.ElapsedTicks, дают одинаковые результаты).

person apdevelop    schedule 04.05.2012

Разрешение таймера снижается до режима 1 мс без особых усилий по реализации. Я только что описал причину точности double в этот ответ. При настройке системы на работу с частотой 1024 прерывания в секунду (с использованием API мультимедийного таймера) время между прерываниями составляет 0,9765625 мс. Стандартное разрешение для синхронизации составляет 100 нс. Эти значения хранятся как целые числа. Значение 0,9765625 нельзя сохранить без потери точности целого числа при разрешении 100 нс. Последняя цифра (5) представляет 500 пс. Таким образом, разрешение должно быть на три порядка выше. Сохранение этих временных значений в виде целых чисел с разрешением 100 пс безнадежно, поскольку 8-байтовое целое число с разрешением 100 пс обернет примерно 21350 дней или примерно 58 лет. Этот промежуток времени слишком короток, чтобы кто-либо мог его принять (вспомните сценарий 2000 года!).

Смотрите ответ, связанный с, чтобы узнать больше о деталях.

person Arno    schedule 24.07.2012