Вопрос по sleep, timer, .net – Почему минимальный интервал Threading.Timer 15 мс, несмотря на timeBeginPeriod (1)

3

Следующий фрагмент

    [DllImport("winmm.dll", EntryPoint = "timeBeginPeriod")]
    public static extern uint TimeBeginPeriod(uint uMilliseconds);

    static void Main(string[] args)
    {
        if (TimeBeginPeriod(1) != 0)
            Console.WriteLine("TimeBeginPeriod failed!");

        Console.WriteLine("Sleep");
        Stopwatch sw = Stopwatch.StartNew();
        for (int i = 0; i < 10; i++)
        {
            Thread.Sleep(1);
            Console.WriteLine(sw.ElapsedTicks * 1000d / Stopwatch.Frequency);
            sw.Restart();
        }

        Console.WriteLine("Threading.Timer");
        sw = null;
        System.Threading.Timer t = null;
        int n = 0;

        t = new Timer(state =>
        {
            if (sw == null)
                sw = Stopwatch.StartNew();
            else
            {
                Console.WriteLine(sw.ElapsedTicks * 1000d / Stopwatch.Frequency);
                n++;
                sw.Restart();
            }
            if (n == 10)
                t.Change(Timeout.Infinite, Timeout.Infinite);
        }, null, TimeSpan.FromMilliseconds(1), TimeSpan.FromMilliseconds(1));
        Console.ReadKey();
    }

будет производить, например, этот вывод:

Sleep
0.151834939915548
0.757358826331279
0.786901687225611
0.712520725399457
0.715593741662697
0.798704863327602
0.5724889615859
0.648825479215934
0.436927039609783
0.517873081634677
Threading.Timer
15.5841035662354
14.8620145856526
15.1098812837944
14.4202684978119
15.3883384620112
14.7210748852159
15.307462261265
15.7125416777831
14.5991320125882
15.6035194417168

По данным сети, напримеркомментарий Ганса Пассанта,timeBeginPeriod влияет на обычные (.net) таймеры. Так почему мой таймер все еще имеет такую грубую гранулярность?Thread.Sleep кажется, просто отлично.

Может быть уместно: это работает на Windows 7, 64-битной, .net 4, внутри VMWare.

Ваш Ответ

1   ответ
5

что мультимедийный таймер не влияет на таймеры .NET. То есть это неизменить минимальный поддерживаемый период времени, который составляет около 15 мс. Этоможет быть улучшить их точность. То есть, если вы попросите 16 мс, вы можете получить 16 мс, а не "где-то между 15 и 30 мс. "

Почему таймеры .NET ограничены 15 мс, мне непонятно.

Там's некоторая информация об этом в принятом ответеВот.

Если ты'ищите таймер с более высоким разрешением для .NET, вы, вероятно, не должныt использовать мультимедийные таймеры. Они были объявлены устаревшими в Windows API. Используйте таймеры очереди таймера. Смотрите мои статьи:

Разрешение таймера .NETИзучение вариантов для лучших таймеровИспользование API-интерфейса Windows Timer Queue

Другой вариант заключается в использованииТаймер ожидания, Полный источник для этого доступен вhttp://www.mischel.com/pubs/waitabletimer.zip

Похожие вопросы