我试图深入了解 Timer 将如何使用线程池。我写了以下简单的片段。
class Program
{
static private readonly Action Action = () => {
Thread.SpinWait(100 * 10000);
Interlocked.Increment(ref _data);
};
private static volatile int _data;
static private Timer _threadCountChecker = new Timer(
(obj) =>
{
var t = Process.GetCurrentProcess().Threads;
Console.WriteLine("Using {0} threads.", t.Count);
Console.WriteLine(Program._data);
}, null, TimeSpan.FromSeconds(1), TimeSpan.FromSeconds(1));
static void Main(string[] args)
{
var l = new List<Timer>();
for (int i = 0; i < 10; i++)
{
l.Add(new Timer((obj) => Action(), null, TimeSpan.FromSeconds(1), TimeSpan.FromSeconds(1)));
}
var exitEvent = new ManualResetEvent(false);
exitEvent.WaitOne();
}
}
令人惊讶的是,这是我得到的输出:
Using 14 threads. 10 Using 14 threads. 18 Using 14 threads. 28 Using 14 threads. 39 Using 14 threads. 48 Using 15 threads. 58 Using 15 threads. 69 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80 Using 15 threads. 80
无论我继续运行进程多长时间,数据变量都保持在 80。
有谁知道为什么变量在前 8 次迭代中得到更新并停止递增?
最佳答案
计时器得到了垃圾回收。在 eventWait.WaitOne() 调用之后添加此语句以解决此问题:
GC.KeepAlive(l);
GC 在发布版本中处理局部变量的方式在 this answer 中有详细解释。 .
关于c# - System.Threading.Timer 的奇怪行为,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19122353/