gpt4 book ai didi

.net - 多线程环境中的对象生存期

转载 作者:行者123 更新时间:2023-12-03 13:13:15 25 4
gpt4 key购买 nike

System.Timers.Timer之后,我创建了一个控制台应用程序来进行练习:

public class Program
{
//private static System.Timers.Timer aTimer;

public static void Main()
{
short_running_method();

Console.WriteLine("Press the Enter key to exit the program.");
Console.ReadLine();


}

static void short_running_method()
{
// Normally, the timer is declared at the class level,
// so that it stays in scope as long as it is needed.
// If the timer is declared in a long-running method,
// KeepAlive must be used to prevent the JIT compiler
// from allowing aggressive garbage collection to occur
// before the method ends. You can experiment with this
// by commenting out the class-level declaration and
// uncommenting the declaration below; then uncomment
// the GC.KeepAlive(aTimer) at the end of the method.
System.Timers.Timer aTimer;

// Create a timer with a ten second interval.
aTimer = new System.Timers.Timer(10000);

// Hook up the Elapsed event for the timer.
aTimer.Elapsed += new ElapsedEventHandler(OnTimedEvent);

// Set the Interval to 2 seconds (2000 milliseconds).
aTimer.Interval = 2000;
aTimer.Enabled = true;

// If the timer is declared in a long-running method, use
// KeepAlive to prevent garbage collection from occurring
// before the method ends.
//GC.KeepAlive(aTimer);
}


// Specify what you want to happen when the Elapsed event is
// raised.
private static void OnTimedEvent(object source, ElapsedEventArgs e)
{
Console.WriteLine("The Elapsed event was raised at {0}", e.SignalTime);
}
}

我知道(如果我错了,请纠正我)只要程序正在运行并且在事件不断触发时,在类级别声明的计时器对象仍然有效。通过注释掉已声明的类级别的计时器对象,并取消注释short_running_method中的声明,我假设如果未使用GC.KeepAlive(aTimer)并且事件应停止触发,则应在一定时间后对atimer对象进行垃圾回收。但是,在我的实验中,该事件似乎从未停止,即使30分钟后它仍在上升。有人可以弄清楚为什么会这样吗?

最佳答案

问题出在从事件源到事件监听器的强引用中:

aTimer.Elapsed += new ElapsedEventHandler(OnTimedEvent);

因此,您可能在这里寻找 弱事件模式:
Weak Event Patterns on MSDN

另外,要 停止计时器,您可以使用:
aTimer.Stop();

You can also stop timing by setting Enabled to false.

The signal to raise the Elapsed event is always queued for execution on a ThreadPool thread, so the event-handling method might run on one thread at the same time that a call to the Stop method runs on another thread. This might result in the Elapsed event being raised after the Stop method is called. The code example in the next section shows one way to work around this race condition.

MSDN: Timer.Stop Method

关于.net - 多线程环境中的对象生存期,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13105908/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com