比较好的做法:通过标志,在线程中要对标志做相应的处理
然后关闭时,先打开标志,用线程Join来等待结束。

解决方案 »

  1.   

    帮助里的说明:在调用 Abort 方法以销毁线程时,公共语言运行库将引发 ThreadAbortException。ThreadAbortException 是一种可捕获的特殊异常,但在 catch 块的结尾处它将自动被再次引发。引发此异常时,运行库将在取消线程前执行所有 finally 块。由于线程可以在 finally 块中进行未绑定的计算,因此必须调用 Join 方法以保证线程已死亡。Join 是一个阻塞调用,它要到线程实际停止执行后才返回。我不太明白这段说明,我怎样才能避免该异常的抛出(用try-catch不行)
      

  2.   

    标志 不大清楚哎,不过Join不是“阻塞调用线程,直到某个线程终止或者经过了指定的时间为止”么?如果线程是个无限循环,那么程序就其他什么也不做,等在那里了。怎么能起到abort的功能呢?另外你说的标志不会是isalive属性吧?那可是只读的呀。
      

  3.   

    关于abort 异常问题可见
    http://expert.csdn.net/Expert/TopicView1.asp?id=1905252
    我刚回的贴子如果你使用abort 则必须抛出异常,想避免我就不推荐使用abort(你可以使用try 忽略它)但如此的话,线程就无安全可言
      

  4.   

    哦。
    Knight94是说,先abort,然后join,以确保abort的完成吧。
      

  5.   

    ArLi2003在http://expert.csdn.net/Expert/TopicView1.asp?id=1905252中的回帖的确值得关注,刚刚拜读,不过有一点疑惑:
    “变量判断中止”是指在使用abort前线设置相应的变量作记号吗?还是把例子中的thead_2_mustend 设置成false后不用使用abort线程“就可以自然的结束”?
      

  6.   

    把例子中的thead_2_mustend 设置成false后不用使用abort线程“就可以自然的结束”?对
      

  7.   

    哦,我明白ArLi2003的意思了。 你是说在进入某个线程后先判断某个变量,然后决定该线程是正常做工作,还是什么也不做,等到程序结束时自生自灭。这样有些线程虽然没有被abort,但是什么也不做,像行尸走肉一样。
    只是这样的活着不做事的线程占用的系统资源是不是有点浪费?还是这些资源是安全应付的代价呢:)
      

  8.   

    betatong, 至于系统抛出ThreadAbortException看来用Knight94说的标记,也就是Arli2003的变量判断的方法可以避免,而且还增加了你程序的防止死锁的安全性哦~
    感谢ArLi2003的精彩回帖,和betatong的问题,使pipibug学了不少东东:)
      

  9.   

    不不不,不是这个意思,我的意思是在while 体内先判断某变量标志是否是真,以决定是否要继续循环,若结束标志相符,则不循环或跳出循环体直接到class 底部也自然就结束了。比如class a{
     Form1 form1;
     public a(Form1 obj){
       form1 = obj;
     } public void op(){
      while (trur){
       form1.i++;
       // 或其它代码
       if (form1.chkBox_ThreadEnd.Checked) break; //相符就跳出循环
      }
     }
    }
      

  10.   

    ArLi2003(阿利 无业悠民)的方法确实可以避免一些,但我这里有些特殊情况:
    我的例子如下:while(true)
    {
      tcpClient = tcpListener.AcceptTcpClient();   // LINE 3
      ...
    }
    我在循环里有个阻塞的方法,所以它会一直处于第三行的地方,看看有没有什么方法可以解决这个问题。
      

  11.   

    还有就是如果我用 About() 后再用 Join() , 程序会阻塞在Join() 处
      

  12.   

    发现socket 可以设置 Blocking 属性为非阻塞式的,然后再结合上面ArLi2003(阿利 无业悠民)的方法,应该可以搞定。
      

  13.   

    虽然已经结帐,但其实socket 应该使用:if (listener.Pending()) {
     Socket sockServer = listener.AcceptSocket();
    }放在循环体就可以避免堵塞!
      

  14.   

    哦,原来TcpListener可以这样来避免阻塞,再次感谢ArLi2003(阿利)