线程结束不能从新启动,除非新生成线程.释放资源由GC完成,只要是没有用的符合GC条件的,都release.

解决方案 »

  1.   

    线程还有别的状态吗?
    我系统内的线程不知道进入什么状态,连interrupt都不行,一直在占着cpu运行
      

  2.   

    hotenM(五月飓风) 死锁状态
      

  3.   

    线程结束,如何重启呢,thread.run()能重新启动吗
      

  4.   

    老弟,你从哪里听说线程是这四种状态呀?
    线程对于任何语言都一样的,它不属于语言的概念(只是java在语言级上支持多线程)。线程只有如下四种状态:运行,挂起(睡眠),就绪(等待),结束(死亡)。你说的dead就是最后一种,在java中有两种方式,一种是自然结束,一种强制dead,不过为了安全性和稳定性,最好只用第一种。线程运行完了并不代表线程类被回收了,你依然可以再用,再次运行就是。
    另外,java中没有提供自行回收对象,这个是由它的垃圾回收器自动回收,你并不知道何时何地进行这样的处理。所以线程完毕,并不代表资源回收,当然除了数据库连接,网络连接,流连接可以close外(这个也要自己进行释放)。如果你不想多余太多的废弃的对象,你可以在结束后,将线程类的主要域设置为null,它们因为而成为弱引用对象,是优先被垃圾回收器回收的
        好了,老弟,好好看看书,希望你成为高手
      

  5.   

    基本同意hh-fwhy的观点,但是
    “线程运行完了并不代表线程类被回收了,你依然可以再用,再次运行就是。”

    “线程类的主要域设置为null,它们因为而成为弱引用对象”
    好像不太对,也可能使我理解错你的话了第一句话是不是指t.start();等到t结束,还可以t.start()?
    如果你是这样认为的话,那就错了,例子如下
    class CCC 
    {
    public static void main(String[] args) 
    {
    T t = new T();
    t.start();
    //wait for a second till T dead
    try
    {
    Thread.sleep(1000);
    }
    catch (Exception e) {System.out.println(e);}
    t.start();
    }
    }
    class T extends Thread
    {
    public void run()
    {
    System.out.println("Run called");
    }
    };
    结果只有一个Run called打印出来,详情请参阅Core Java Volume 2 第 11 页图第二句话,也很不解,原因有二
    1.释放线程的各个域,应该是此线程的引址计数器为0,也就是说没有Thread的引用指像此线程,通常是t=null,而不是t.name=null;t.sex=null;t.age=null;.......
    2.你说的弱引用应该是这个吧?
    java.lang.Object
      |
      +--java.lang.ref.Reference
            |
            +--java.lang.ref.WeakReference
    这是从JDK1.2开始引入的,WeakReference不会被对象引址计数器记录,所以就算这样的引用仍存在,只要没有普通引用,他就可以被释放。IBM developerworks有一片详述。你用在这里,“将线程类的主要域设置为null,它们因为而成为弱引用对象”我不太懂。
    本人愚见,还请海纳
      

  6.   

    不是我给Horstmann做广告,你真该看看这本书,非常不错
    不过机械工业出版社的老毛病,翻译太一般
      

  7.   

    我的想法是这样的:假设有A,B两个线程,A线程向缓冲区存数据,B线程取数据(处理)。现在我想使A线程存数据的时候,调用B.run(),不知这样做可行性如何,会不会存在什么问题?大家对这种生产-消费问题有什么好的处理方法和建议,不妨讨论讨论
      

  8.   

    线程结束了,线程内的对象是会被自动释放的,不用设置为null ,这个和在其他程序里将不使用的废气品设置为null不一样,因为线程对象结束后,已经被虚拟机处理掉的
      

  9.   

    hh_fwhy(凤舞凰扬) :高手!其他人都不知在说什么,回去多看看书。
      

  10.   

    假设P(producer)和C(Consumer)同时操作缓冲区,而且方法是同步的
    如果P发现缓冲区慢,用wait() block自己,把自己放入等待队列。让C有机会去取。C取完之后,告诉P,你可以继续生产。
    如果C发现缓冲区空,用wait() block自己,把自己放入等待队列。让P有机会去放。P放完之后,告诉C,你可以继续取。
    双方都要notify(),或者notiryAll()
    则此例中,notify和notifyAll一样
    在多个线程的情况下,notifyAll更好一些,
    有个例子public class ThreadTest
    {
    final static int maxOperations = 20;
    static int operatons = 0; WareHouse warehouse = new WareHouse();
    Producer pro = new Producer();
    Consumer con = new Consumer(); public static void main(String[] args) 
    {
    ThreadTest test = new ThreadTest();
    test.beginTest();
    }
    public void beginTest()
    {
    pro.start();
    con.start();
    }
    class Producer extends Thread
    {
    int operations = 0;
    public void run()
    {
    System.out.println("Producer started");
    try
    {
    while(operations < maxOperations)
    warehouse.putIn(++operations);

    }
    catch (Exception e)
    {System.out.println(e); }
    }
    };
    class Consumer extends Thread
    {
    int operations = 0;
    public void run()
    {
    System.out.println("Consumer started");
    try
    {
    while(operations < maxOperations)
    warehouse.fetchOut(++operations);

    }
    catch (Exception e)
    {System.out.println(e); }
    }
    };class WareHouse
    {
    int wares;
    final int MAX_WARES = 5; public synchronized void putIn(int ops)
    {
    try
    {
    while(wares>=MAX_WARES){
    System.out.println("Producer:" + ops + "Warehouse full, I have to wait for consumer!");
    wait();//block me to let consumer have chance to fetchOut
    }
    //After consumer done, the consumer will notify me, Is can continue
    wares++;//put in one
    System.out.println("Producer:" + ops + "I put in one");
    //tell consumer that you can fetch because I have just putIn one
    notifyAll();
    System.out.println("Producer:" + ops + "I tell Consumer that he can fetch");

    }
    catch (Exception e)
    {
    System.out.println(e);
    }
    }
    public synchronized void fetchOut(int ops)
    {
    try
    {
    while(wares<=0){
    System.out.println("Consumer:" + ops + "Warehouse empty, I have to wait for producer!");
    wait();//block me to let producer have chance to putIn
    }
    //After the producer done, producer will notify me, I can continue
    wares--;//fetch one
    System.out.println("Consumer:" + ops + "I fetch one");
    //tell producer that you can putIn because I have just fetch one
    notifyAll();
    System.out.println("Consumer:" + ops + "I tell Producer that he can put in");
    }
    catch (Exception e)
    {
    System.out.println(e);
    }

    }
    };}
    Core Java中线程的最后一部分,讲解了PipedStream实现的版本,非常简单,是自动的,很实用,不过如果你是想做试验理解这个问题,还是看看上面这个程序把,我还写过一个很多线程协作的,道理差不多。这里再附上Horstmann在Core Java中的PipedStream例子
    /**
     * @version 1.20 1999-04-23
     * @author Cay Horstmann
     */import java.util.*;
    import java.io.*;public class PipeTest
    {  public static void main(String args[])
       {  try
          {  /* set up pipes */
             PipedOutputStream pout1 = new PipedOutputStream();
             PipedInputStream pin1 = new PipedInputStream(pout1);         PipedOutputStream pout2 = new PipedOutputStream();
             PipedInputStream pin2 = new PipedInputStream(pout2);         /* construct threads */         Producer prod = new Producer(pout1);
             Filter filt = new Filter(pin1, pout2);
             Consumer cons = new Consumer(pin2);         /* start threads */         prod.start();
             filt.start();
             cons.start();
          }
          catch (IOException e){}
       }
    }class Producer extends Thread
    {  public Producer(OutputStream os)
       {  out = new DataOutputStream(os);
       }   public void run()
       {  while (true)
          {  try
             {  double num = rand.nextDouble();
                out.writeDouble(num);
                out.flush();
                sleep(Math.abs(rand.nextInt() % 1000));
             }
             catch(Exception e)
             {  System.out.println("Error: " + e);
             }
          }
       }   private DataOutputStream out;
       private Random rand = new Random();
    }class Filter extends Thread
    {  public Filter(InputStream is, OutputStream os)
       {  in = new DataInputStream(is);
          out = new DataOutputStream(os);
       }   public void run()
       {  for (;;)
          {  try
             {  double x = in.readDouble();
                total += x;
                count++;
                if (count != 0) out.writeDouble(total / count);
             }
             catch(IOException e)
             {  System.out.println("Error: " + e);
             }
          }
       }   private DataInputStream in;
       private DataOutputStream out;
       private double total = 0;
       private int count = 0;
    }class Consumer extends Thread
    {  public Consumer(InputStream is)
       {   in = new DataInputStream(is);
       }   public void run()
       {  for(;;)
          {  try
             {  double avg = in.readDouble();
                if (Math.abs(avg - old_avg) > 0.01)
                {  System.out.println("Current average is " + avg);
                   old_avg = avg;
                }
             }
             catch(IOException e)
             {  System.out.println("Error: " + e);
             }
          }
       }   private double old_avg = 0;
       private DataInputStream in;
    }
      

  11.   

    calvin_wang(响马) 
    〉“其他人都不知在说什么,回去多看看书。”是你自己看不懂把?你看明白 楼主,kofwr(搭补流二) , ispring() 他们的帖子了么?
      

  12.   

    我的理解是:
    当线程运行结束后,如过它没有被别的类引用的话,那么java 的垃圾回收器会在适当的时候回收该线程所占的资源;如果有别的类引用了该线程,则线程所占用的资源不会被回收,即使线程已经结束。例如下面代码:
    class  A
    {}
      

  13.   

    class A
    {
      B t=new B();  ...}class B extends Thread
    {
    ...
    }不知道我的理解是否正确,请大家指正!!!
      

  14.   

    同意 hh_fwhy(凤舞凰扬) 的观点
      

  15.   

    to pzl686(阿虎),
    你的这种理解好像不太对吧?
    只有在 new 后对象的实例才被分配资源,而且启动后就是一个独立的线程
    在死亡之后被垃圾处理机制回收。
    问题就在是什么时候回收,好像没看到什么这方面的资料?
    所以你的 A B 的例子是有问题的
     
      

  16.   

    不同意 hh_fwhy(凤舞凰扬) 的观点