我有主线程(MainThread),我在其上创建了新的thred(让我们称之为NewThread)。在NewThread中,我调用一个想要为MainThread调用某个方法的方法。
问题在于,当我从MainThread调用NewThread.Join()时,NewThread中的Invoke方法无法完成/终止(并且整个应用程序永远冻结......)因为MainThread正在等待NewThread终止... < / p> 像恶性循环一样......任何想法如何解决?我需要有可能从MainThread终止/中止NewThread并且不再存在NewThread。
我希望我足够具体。
主线程:
void method()
{
if(currentthread!=null)
{
currentthread.Join();
currentthread=null;
}
sth...
Backgroundworker worker = new Backgroundworker();
worker.DoWork += delegate (...)
{
currentthread=Thread.CurrentThread;
Func();
}
....
}
NewThread:
delegate void FuncDel();
void Func()
{
if(MainThread.InvokeRequired)
{
FuncDel funcD = new FuncDel();
MainThread.InvokeRequired(funcD);
return;
}
....
}
答案 0 :(得分:2)
嗯,显而易见的答案是,如果工作线程有可能尝试在主线程上调用Invoke(),那么你的主线程永远不应该是Join()你的工作线程。
如果你只是使用Join()来等待主线程上的关闭,你应该首先做一些像Thread.Abort(),或者更好的是,使用线程同步对象,如Mutex或共享变量,向工作线程表明它需要中止。一旦你发信号通知工作线程中止,然后允许你的主线程加入()它;在尝试在主线程上调用方法之前,你的工作线程应该总是检查它是否已经中止。
如果由于其他原因使用Join(),则应再次查看线程同步对象,如Mutex。这些允许你的线程等待彼此发送它们的信号 - 你的工作线程可以在需要调用Invoke()之前“唤醒”你的主线程,以确保你的主线程获得CPU时间来完成它的工作。
答案 1 :(得分:0)
这就是Thread.Join所做的,它会阻塞你的调用线程,直到Joined线程终止。我想如果你只是想在另一个线程上调用,我不知道你为什么要使用join。如前所述,代码将有助于澄清情况。
如果您的实现不允许您阻止主线程,则可以轮询ThreadState以检查线程的状态与使用Join。
答案 2 :(得分:0)
听起来你几乎想要取消模式。试试这个TPL选项:
CancellationTokenSource cts = new CancellationTokenSource();
Task.Factory.StartNew(() =>
{
if(cts.Token.IsCancellationRequested)
return;
// Do Stuff
});
您基本上可以为您要执行的操作启动任务,如果您需要取消它,您只需致电
cts.Cancel();
你的例子很复杂;旋转一个线程来调用某个方法与原始线程无关。