Thread.Sleep() resolution varies from 1 to 15.6ms
Given this console app:
class Program
{
static void Main()
{
int outer = 100;
int inner = 100;
Stopwatch sw = new Stopwatch();
for (int j = 0; j < outer; j++)
{
int i;
sw.Restart();
for (i = 0; i < inner; i++)
Thread.Sleep(1);
sw.Stop();
Console.WriteLine(sw.ElapsedMilliseconds);
}
}
}
I expected the output to be 100 numbers close to 100. Instead, I get something like this:
99 99 99 100 99 99 99 106 106 99 99 99 100 100 99 99 99 99 101 99 99 99 99 99 101 99 99 99 99 101 99 99 99 100 99 99 99 99 99 103 99 99 99 99 100 99 99 99 99 813 1559 1559 1559 1559 1559 1559 1559 1559 1559 1559 1559 1559 1559 1559 1559 1559 1559 1559 1559 1559 1560 1559 1559 1559 1559 1558 1558 1558 1558 1558 1558 1558 1558 1558 1558 1558 1558 1558 1558 1558 1558 1558 1558 1558 1559 1558 1558 1558 1558 1558
But sometimes I won't get any accurate results; it will be ~1559 every time.
Why isn't it consistent?
Some googling taught me that 15.6ms is the length of a timeslice, so that explains the ~1559 results. But why is it that I sometimes get the right result, and other times I just get a multiple of 15.6? (e.g. Thread.Sleep(20) will usually give ~31.2ms)
How is it affected by hardware or software?
I ask this because of what led me to discover it:
I had been developing my application on a 32 bit dual-core machine. Today my machine was upgraded to 64bit quad-core with a complete OS re-install. (Windows 7 and .NET 4 in both cases, however I can't be sure the older machine had W7 SP1; the new one does.)
Upon running my application on the new machine, I immediatey notice my forms take longer to fade out. I have a custom method to fade my forms which uses Thread.Sleep() with values varying from 10 to 50. On the old system this seemed to work perfectly every time. On the new system it's taking much longer to fade than it should.
Why did this bahavior change between my old system and my new system? Is this related to hardware, or software?
Can I make it consistently accurate? (~1ms resolution)
Is there something I can do in my program to make Thread.Sleep() reliably accurate to about 1ms? Or even 10ms?
See Question&Answers more detail:os