原贴:http://community.csdn.net/Expert/TopicView3.asp?id=4371270
public class Test {

public static void main(String[] args) {
try {
ThreadApp ta = new ThreadApp();
for (int i = 0; i < 5; i++) {
new Consumer(String.valueOf(i), ta);
System.err.println(" " + i);
System.err.println(" ");
} } catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
System.exit(1);
}
}class Consumer extends Thread {

private ThreadApp ta = null;
private String id = null;

public Consumer(String id, ThreadApp ta) {
this.id = id;
this.ta = ta;
this.start();
}

public void run() {
try {
ta.fireCommand(id + " : " + String.valueOf(System.currentTimeMillis()));
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}import java.util.Hashtable;
import java.util.Vector;public class ThreadApp extends Thread {

private Vector queue = new Vector();

private Hashtable ret = new Hashtable();

public ThreadApp() {
this.start();
System.out.println("currentThread in construt ThreadApp : " + Thread.currentThread());
}

public void run() {
System.out.println("currentThread in run : " + Thread.currentThread());
while (true) {
while (queue.size() > 0) {
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
String cmd = (String) queue.remove(0);
ret.put(cmd, String.valueOf(System.currentTimeMillis()));
synchronized (cmd) {
cmd.notify();
}
cmd = null;
}
}
}

public String fireCommand(String cmd) throws InterruptedException {
System.out.println("currentThread in fireCommand : " + Thread.currentThread());
String innerCmd = cmd + System.currentTimeMillis();
queue.add(innerCmd);
synchronized (innerCmd) {
innerCmd.wait();
}
System.out.println("innerCmd is " + innerCmd);
String rv = (String) ret.get(innerCmd);
System.out.println("return value is " + rv);
return rv;
// return (String) ret.get(innerCmd);
}
}

解决方案 »

  1.   

    我先说说结构
    你看你的class Consumer extends Thread {
    public Consumer(String id, ThreadApp ta) {
    你聚合了一个ThreadApp 也就是我们说的producer吧这是很明显的紧偶合,我上贴已说过,这样的结构不好,你先把uml的class图画清楚。我知道你用Vector是想省去同步,但这不好,你这个程序看似能运行,但难扩展,因为我们需要在自己构造的Vector里进行聚合其他的事物(对象)。我这里就不列举Vector的效率有多低了,反正低到无法忍受的地步,当然我是指大批量的用户群。你先这样:把Vector写成一个对象,再试验一下,看看效果。
    就象这样
    public class CmdContainer{
       这里维护一个循环数组.   synchronized put(){
        数组满了则wait
        notifyAll();}   synchronized get(){
      如果数组等于0或小于0则wait
       notifyAll();}}
    了解否?如果你想维护池,我可以再给你发贴
      

  2.   

    晕,我的rational modeler又过期了,你自己动手UML吧
      

  3.   

    不用了,我还不会玩UML,eclipse有插件嘛
      

  4.   

    我还是那段,你的fireCommand定义为static是没太多意义的!class Commander
    {
    public void _wait()
    {
    syn...(this){wait();}
    }
    public void _notify()
    {
    syn..(this){notify();}
    }public fireCommand(cmd)
    {
    //将this和cmd对应一起存入Queue;
    _wait();
    }
    }
      

  5.   

    谢谢楼上,我的fireCommand不是static的,我觉得你这段代码比较安全,但是我不想和外部调用者的耦合度太高了,所以用cmd来wait和notify,但有人说String很特别不适合用来wait和notify.Why?
      

  6.   

    但有人说String很特别不适合用来wait和notify.Why?不应该拿String来wait和notify,既然你可以显然wait和notify是object的方法。
    而我用的wait和notify可没有用在String上,如果你明白,应该看的出来我的wait和notify是用在线程上的,而且只要把CmdContainer整出来,producer就可以很多也无所谓。notify在其实在线程的程序里是不应该用到的,应该用notifyAll(),原因太多了,我解释三贴估计也许能解释清楚