Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/270.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 线程已在Windows窗体中退出,代码为0_C#_.net_Multithreading_Winforms - Fatal编程技术网

C# 线程已在Windows窗体中退出,代码为0

C# 线程已在Windows窗体中退出,代码为0,c#,.net,multithreading,winforms,C#,.net,Multithreading,Winforms,我在Windows窗体中退出线程时遇到问题 我有经典的Windows窗体,它正在运行。我每段时间都需要做一些事情,所以我补充道: TimerCallback timerDelegate = new TimerCallback(this.TryDoSomething); int period = 10 * 1000; // to miliseconds System.Threading.Timer stateTimer = new System.Threading.Timer(timerDeleg

我在Windows窗体中退出线程时遇到问题

我有经典的Windows窗体,它正在运行。我每段时间都需要做一些事情,所以我补充道:

TimerCallback timerDelegate = new TimerCallback(this.TryDoSomething);
int period = 10 * 1000; // to miliseconds
System.Threading.Timer stateTimer = new System.Threading.Timer(timerDelegate, null, period, period);
方法DoSomething由几个线程(主线程和这个计时器)调用,因此我以这种方式介绍了它:

private void TryDoSomething(object o)
        {
            lock (tryDoSomethingMutex)
            {
                if (this.dataGridView1.InvokeRequired)
                {
                    RefreshCallback d = new RefreshCallback(DoSomething);
                    this.Invoke(d, new object[] { o });
                }
                else
                {
                    this.DoSomething(o);
                } 
            }
        }
一切正常,直到我的计时器线程带着消息退出:

The thread 0x2798 has exited with code 0 (0x0).
同样的事情也发生在我的FileSystemWatcher上,它也调用DoSomething方法。 这两个事件都是独立的,在随机时间退出(至少我没有找到任何规则)


造成这种情况的原因是什么?我如何防止它?

听起来计时器正在被垃圾收集。将其作为表单的实例变量,以便保留引用。

如果不保留对计时器对象的引用,它将被垃圾收集

查看您发布的代码,您似乎没有保留引用。您需要将其设置为包含类中的字段,而不是局部变量

如果在长时间运行的方法开始时声明计时器,并且以后在方法中不引用它,则计时器也可能被垃圾回收


您可以通过添加
GC.KeepAlive(计时器)来解决这个特定问题接近方法结尾。

这不是错误,它只是指示线程已完成执行。直到线程退出为止?所以这不是为了退出?你不是设定决斗时间的人吗?这就是问题所在——我不是。定时器被设置为在每一段时间内做一些事情,并突然在随机时间内退出(但没有任何错误)。当然这是正确的答案,谢谢!现在,当我想到这一点时,它似乎很明显。误导我的是,当声明线程的方法在“很久”以前结束时,线程通常要花一分钟以上的时间才能退出。所以垃圾收集器花了大约一分钟(有时甚至两分钟或更长时间)才发现它是垃圾,应该被处理掉?为什么这么长时间?除非内存越来越低,否则垃圾收集器通常不会经常运行,以减少开销;我想这就是为什么花了这么长时间。这是有道理的。谢谢:)为了完全准确,我真的应该说“第2代垃圾收集往往不会经常运行”。第0代会频繁运行,但计时器可能会保留到第2代。