- c - 在位数组中找到第一个零
- linux - Unix 显示有关匹配两种模式之一的文件的信息
- 正则表达式替换多个文件
- linux - 隐藏来自 xtrace 的命令
简而言之:我从我的表单启动一个线程,然后在一段时间后对其使用 Join 方法。它终止了,但我的应用程序卡在了 Join 上,并且拒绝承认它已完成加入。什么会导致这种情况发生?我的线程是从表单上的一个按钮启动的,并尝试从同一表单上的第二个按钮加入。
更多信息:我有一个使用线程来完成通信和数字运算的应用程序。假设Main Form是父线程,第一个子线程是Child1。启动后,Child1 与外部设备建立了一些通信并启动了它自己的 2 个子线程(Child2 和 Child3)来处理传入的数据。
当用户决定应用程序停止处理传入数据时,我需要 Child1 终止(因此如果需要,可以在恢复之前更改 com 设置)。我设置了一个停止事件并且 Child1 退出其执行循环,它所做的第一件事是通知 Child2 和 Child3 不再需要它们(通过另一个停止事件),Child2 和 Child3 等待 Child1 中的 Join 方法。这很好用。
不起作用的是,在设置提示 Child1 退出其运行循环并终止的停止事件之后,表单还在 Child1 上使用了 Join 方法,但是,此 Join 会无限期地等待。
逐步执行:当我逐步执行我的应用程序时,我注意到在使用 Join 之前,IsAlive 属性为 true。在我点击 Child1.Join() 后,我无法再从线程中获取任何信息,因为它位于“JoinWaitSleep”中。但是,如果我运行一个 while 循环导致表单线程在 Child1.IsAlive 为 true 时休眠,这就可以正常工作。我的第二个按钮是否以某种方式成为无法将 Child1 连接到它的线程的一部分?
public void Run()
{ //Known as Child1
//code to setup coms is here
//Launch Builder threads
InsertBackgroundMonitor("Launching Collector Threads");
RunBuilders = true;
//Known as Child2 and Child3
BuildThread1 = new Thread(new ThreadStart(Cam1Builder));
BuildThread2 = new Thread(new ThreadStart(Cam2Builder));
BuildThread1.Start();
BuildThread2.Start();
while (!StopEventHandle.WaitOne(0, true))
{
//// Code that waits for coms and tosses data into lists
}
RunBuilders = false;
//Wait for threads to terminate
BuildThread1.Join();
BuildThread2.Join();
}
private void RunButton_Click(object sender, System.EventArgs e)
{
//Button for running the control thread
ControlThread = new Thread(new ThreadStart(Run));
ControlThread.Start();
}
private void StopButton_Click(object sender, System.EventArgs e)
{
if (btnStop.Enabled)
{ //Button for stopping the control thread
StopEventHandle.Set();
if (ControlThread != null)
{
while (ControlThread.IsAlive)
{
Thread.Sleep(100);
}
//somehow Join did not work
//ControlThread.Join();
}
//Update buttons
btnStart.Enabled = true;
btnStop.Enabled = false;
}
}
最佳答案
没有更多代码很难说,但是您有一些您已经启动但没有正确关闭的资源。
Join() 等待线程完全关闭,并在返回之前释放所有资源。如果 Thread 有任何 BackgroundWorker 任务,或者如果它有任何您没有显示的备用任务仍在运行,它将不会返回。
由于 BuildThread1 和 BuildThread2 都正确返回并加入,您可以确定它不是其中之一,也不是它们正在做的任何事情。查看其余代码。它有什么作用?
编辑:这很好用:
namespace WindowsFormsApplication1
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
Thread ControlThread;
Thread BuildThread1;
Thread BuildThread2;
volatile bool RunBuilders = true;
volatile bool RunControl = true;
private void button1_Click(object sender, EventArgs e)
{
ControlThread = new Thread(new ThreadStart(Run));
ControlThread.Start();
}
private void button2_Click(object sender, EventArgs e)
{
RunControl = false;
if (ControlThread != null)
{
while (ControlThread.IsAlive)
{
Thread.Sleep(100);
}
//somehow Join did not work
ControlThread.Join();
}
}
public void Run()
{ //Known as Child1
//code to setup coms is here
//Launch Builder threads
RunBuilders = true;
//Known as Child2 and Child3
BuildThread1 = new Thread(new ThreadStart(Cam1Builder));
BuildThread2 = new Thread(new ThreadStart(Cam1Builder));
BuildThread1.Start();
BuildThread2.Start();
while (RunControl)
{
//// Code that waits for coms and tosses data into lists
}
RunBuilders = false;
//Wait for threads to terminate
BuildThread1.Join();
BuildThread2.Join();
}
public void Cam1Builder()
{
while ( RunBuilders )
{
}
}
}
}
关于c# - 在 "IsAlive"属性为 false 后,Join 拒绝承认子线程已终止。 C#,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6427079/
我有一个 MyTunnel 类,它扩展了 Thread 类: public class MyTunnel extends Thread { protected Object obj;
我收到此错误: "non-static method isAlive() cannot be referenced from a static context" 这段代码有什么问题..请。 我想检测线
我需要一些有关 isAlive() 和 join() 函数的帮助。我了解如何以以下形式实现 isAlive() 和 join(): public class mthread implements Ru
我是多线程新手;这是启动线程的正确方法吗? if(!sesThread.isAlive()) { try { sesThread.start(); }catch(Ill
我正在尝试使用 isALive 和 join 方法,但它抛出一个错误,如找不到符号....请告诉我这个程序中的错误到底在哪里。join 方法的用途是什么。我知道这是等待线程完成,但我想要详细信息。 c
我正在寻找一种方法来在对象引用被垃圾回收时偷偷调用回调函数。 我知道我可以将对象包装在一个弱引用中,但我仍然需要轮询一组引用以了解状态更改。 我宁愿不进行轮询,因为当什么都没有发生时,这似乎是在浪费
在 Web Controller 中,我有一个接收请求的父线程。有些请求需要很长时间才能处理。为了防止客户端超时,我将父线程设置为每 2 秒发回一个字节,而子线程正在执行操作的耗时部分。 我想确保我考
这个问题已经有答案了: Thread.isAlive() vs Thread.join() (3 个回答) 已关闭 9 年前。 有两种方法可以确定线程是否已完成。首先,您可以调用isAlive()在线
当我调用 isAlive() 时,我看到的代码形式如下:m.thrd.isAlive()。 m 实现可运行接口(interface)。 thrd 是 Thread 的对象。 我理解isAlive()是
作为 this question 的后续行动,我有以下代码: using System; using System.Runtime.InteropServices; namespace Console
如解释here ,如果 WeakReference 的 IsAlive 返回 true,则它不可信任。现在,我正在尝试了解 correct way使用这个: 不正确: WeakReference do
这个问题在这里已经有了答案: How can I wait for a thread to finish with .NET? (11 个答案) 关闭 3 年前。 我在标签点击事件中启动了一个线程。
我正在写一个函数 IsAlive采取IObservable , 和时间跨度,并返回 IObservable规范用例是检测流服务器是否仍在发送数据。 我为此提出了以下解决方案,但觉得它的工作原理并不是最
我开始知道下面的代码输出为 false ,但是当我们看到这个 Thread 实例时,我们创建的 thread 被设置为守护进程并且仍在运行,那么为什么方法调用 thread.isAlive() 会返回
有一个名为r1的可运行方法 Runnable r1=new Runnable(){ @Override public void run(){ //some code here
我有一些java脚本来检查小程序是否在加载页面的其余部分之前完成加载。它已经工作了很多年,现在似乎在 Firefox 16 和 IE 7 中失败。它在 IE 8 中工作 关于它为何损坏以及如何修复它有
如果我遍历 Weakreference 列表,在通过 _ref.IsAlive 验证后,我如何确定该引用仍然存在? 例如我有这段代码,其中 scopeReferences 是 Weakreferenc
这个问题已经有答案了: Why does an IllegalThreadStateException occur when Thread.start is called again (7 个回答)
我有两个按钮,当用户单击第一个按钮时,它将启动一个线程来更新 UI,当用户单击第二个按钮时,应用程序将为第一个线程设置一个 boolean 变量以不允许它更新线程,然后它将启动第二个线程。这是我的 R
为什么 isAlive() 方法在 Thread.java 中被声明为 native?哪个类实现了这个?我知道 native 方法是在 Java 之外实现的。实现它的类是通过加载相应的库来加载的。但是
我是一名优秀的程序员,十分优秀!