再帖一个类:package table;import java.io.Serializable; import java.awt.Color;public class LightStatus implements Serializable {long id; int tabid,subid,status,total,counter; Color lights[]; boolean flag;
public LightStatus() {lights=new Color[Table.MAXPLAYERS]; } public long getID() {return id;} public int getTableID() {return tabid;} public int getSubID() {return subid;} public int getCounter() {return counter;} public int getStatus() {return status;} public int getTotal() {return total;} public synchronized void setGreen(int n) {lights[n]=Color.green; counter++; status++; if(counter==total) flag=false;} public synchronized void setRed(int n) {lights[n]=Color.red; status++; flag=false;} public synchronized Color getLight(int n) {if(n<0 || n>lights.length-1) return null; return lights[n]; } public Color [] getLights() {return lights;} public boolean getFlag() {return flag;} public void prepare(long i,int t1,int t2) {id=i; tabid=t1; total=t2;} public void reset(int n) {subid=n; status=0; counter=0; flag=true; for(int i=0;i<total;i++) lights[i]=Color.yellow; } public void print() {for(int i=0;i<total;i++) {System.out.println(i+")"+lights[i].toString()); } } }
偶可以把代码都帖出来,但真的会有人研究吗?(为了测试方便,偶还加了bug变量)package link;import java.util.*;
import java.net.*;
import java.awt.*;
import java.awt.event.*;import table.Confirmee;
import table.Table;
import table.LightBox;
import table.LightStatus;public class ConfirmDialog extends Dialog implements Observer
{Confirmee cf; Label lb,lights[]; int bug=0;
public ConfirmDialog(Frame f,Confirmee m)
{super(f,false); cf=m;
GridBagLayout gbl=new GridBagLayout(); setLayout(gbl);
GridBagConstraints c=new GridBagConstraints();
lights=new Label[Table.MAXPLAYERS];
Panel p=new Panel(); byte a[]=new byte[1]; a[0]=64; String s;
for(int i=0;i<Table.MAXPLAYERS;i++)
{a[0]++; s=new String(a);
lights[i]=new Label(s,Label.CENTER); p.add(lights[i]);
}
c.gridx=0;c.gridy=0; gbl.setConstraints(p,c); add(p);
lb=new Label("Continue?",Label.CENTER);
c.gridx=0;c.gridy=1; gbl.setConstraints(lb,c); add(lb); p=new Panel(); Button b=new Button("Yes"); p.add(b);
b.addActionListener(new ConfirmListener());
b=new Button("No"); p.add(b);
b.addActionListener(new ConfirmListener());
b=new Button("Close"); p.add(b); // b.addActionListener(new ConfirmListener());
c.gridx=0;c.gridy=2; gbl.setConstraints(p,c); add(p); pack(); setLocationRelativeTo(null);m.addObserver(this);
} class ConfirmListener implements ActionListener
{public void actionPerformed(ActionEvent e)
{String s=e.getActionCommand();
if(s.equals("Yes")) cf.confirm(true);
if(s.equals("No")) cf.confirm(false);
}
} public void update(Observable o1,Object o2)
{
LightStatus s=cf.getLightStatus();
// if(Color.red.equals(b.getLight())) {setVisible(false); return;}
// if(b.allGreen()) setVisible(false);
bug++; System.out.println("Time="+cf.getTime()+" bug="+bug);
if(cf.getTime()==-1) return; setVisible(true);
// if(cf.getTime()!=-1) if(s==null) return;
byte c[]=new byte[1]; c[0]=64; String t;
for(int i=0;i<Table.MAXPLAYERS;i++)
{c[0]++; t=new String(c); if(i==cf.getSeat()) t="Me";
lights[i].setText(t); lights[i].setBackground(s.getLight(i));
if(i>s.getTotal()-1) lights[i].setEnabled(false);
else lights[i].setEnabled(true);
}
if(s.getSubID()>1) lb.setText("Continue? ("+cf.getTime()+")");
else lb.setText("About to begin, pls click Yes ("+cf.getTime()+")");
pack(); System.out.println("21 "+bug);
if(s.getCounter()==s.getTotal()) {setVisible(false); System.out.println("22 "+bug);}
}
}
package link;import java.util.*;
import java.net.*;
import java.awt.*;
import java.awt.event.*;import table.Confirmee;
import table.Table;
import table.LightBox;
import table.LightStatus;public class ConfirmDialog extends Dialog implements Observer
{Confirmee cf; Label lb,lights[]; int bug=0;
public ConfirmDialog(Frame f,Confirmee m)
{super(f,false); cf=m;
GridBagLayout gbl=new GridBagLayout(); setLayout(gbl);
GridBagConstraints c=new GridBagConstraints();
lights=new Label[Table.MAXPLAYERS];
Panel p=new Panel(); byte a[]=new byte[1]; a[0]=64; String s;
for(int i=0;i<Table.MAXPLAYERS;i++)
{a[0]++; s=new String(a);
lights[i]=new Label(s,Label.CENTER); p.add(lights[i]);
}
c.gridx=0;c.gridy=0; gbl.setConstraints(p,c); add(p);
lb=new Label("Continue?",Label.CENTER);
c.gridx=0;c.gridy=1; gbl.setConstraints(lb,c); add(lb); p=new Panel(); Button b=new Button("Yes"); p.add(b);
b.addActionListener(new ConfirmListener());
b=new Button("No"); p.add(b);
b.addActionListener(new ConfirmListener());
b=new Button("Close"); p.add(b); // b.addActionListener(new ConfirmListener());
c.gridx=0;c.gridy=2; gbl.setConstraints(p,c); add(p); pack(); setLocationRelativeTo(null);m.addObserver(this);
} class ConfirmListener implements ActionListener
{public void actionPerformed(ActionEvent e)
{String s=e.getActionCommand();
if(s.equals("Yes")) cf.confirm(true);
if(s.equals("No")) cf.confirm(false);
}
} public void update(Observable o1,Object o2)
{
LightStatus s=cf.getLightStatus();
// if(Color.red.equals(b.getLight())) {setVisible(false); return;}
// if(b.allGreen()) setVisible(false);
bug++; System.out.println("Time="+cf.getTime()+" bug="+bug);
if(cf.getTime()==-1) return; setVisible(true);
// if(cf.getTime()!=-1) if(s==null) return;
byte c[]=new byte[1]; c[0]=64; String t;
for(int i=0;i<Table.MAXPLAYERS;i++)
{c[0]++; t=new String(c); if(i==cf.getSeat()) t="Me";
lights[i].setText(t); lights[i].setBackground(s.getLight(i));
if(i>s.getTotal()-1) lights[i].setEnabled(false);
else lights[i].setEnabled(true);
}
if(s.getSubID()>1) lb.setText("Continue? ("+cf.getTime()+")");
else lb.setText("About to begin, pls click Yes ("+cf.getTime()+")");
pack(); System.out.println("21 "+bug);
if(s.getCounter()==s.getTotal()) {setVisible(false); System.out.println("22 "+bug);}
}
}
偶觉得明显执行过setVisible(false),但对话窗口没被关掉No.0 Client
r:len=423
Time=-1 bug=1
r:len=423
Time=1 bug=2
21 2
r:len=423
Time=2 bug=3
21 3
r:len=423
Time=3 bug=4
21 4
r:len=435
Time=3 bug=5
21 5
Time=4 bug=6
21 6
r:len=435
Time=5 bug=7
21 7
r:len=435
Time=6 bug=8
21 8
r:len=423
Time=6 bug=9
21 9
22 9
Time=7 bug=10
21 10
22 10
Time=-1 bug=11
偶把setVisible(false)改成dispose(),效果好像还可以偶想搞清楚的是:这究竟是偶程序的错,还是JDK的错?
如果不是偶的错,偶就有信心了再帖一个类的代码:
(坛子规定最多只能连发三帖,好像不太方便)package table;import java.util.*;
import java.io.Serializable;
import java.awt.Color;
import java.awt.*;import link.*;
import guai.GuaiType;
//import guai.GuaiEngine;public class Confirmee extends Observable implements Runnable,Listener
{public static final int MAXTIME=20;
Receiver2 input; MyLight ml; LightStatus ls; int time; //boolean flag;
public static void main(String args[])
{if(args.length!=1) {System.out.println("One Arg Pls!"); return;}
int n;
try
{n=Integer.parseInt(args[0]); System.out.println("No."+n+" Client");
Receiver2 r=new Receiver2(n); Confirmee cf=new Confirmee(r);
cf.setSeat(n);
Frame f=new Frame(); ConfirmDialog cd=new ConfirmDialog(f,cf);
}
catch(Exception e) {System.out.println(e.toString());}
} public Confirmee(Receiver2 r)
{input=r; input.addListener(this); ml=new MyLight(); ls=null; time=-1;} public MyLight getMyLight() {return ml;}
public LightStatus getLightStatus() {return ls;}
public Color [] getLights() {return ls.getLights();}
public int getSeat() {return ml.getSeat();}
public void setSeat(int s) {ml.setSeat(s);}
public int getTime() {return time;}
// public int getTimeout() {return MAXTIME-time;} private boolean update(LightStatus s)
{
if(ls==null)
{ls=s; ml.reset(s.getID(),s.getSubID()); return true;} if(ls!=null) if(ls.getID()<s.getID())
{ls=s; ml.reset(s.getID(),s.getSubID()); return true;}
if(ls!=null) if(ls.getID()==s.getID() && ls.getSubID()<s.getSubID())
{ls=s; ml.reset(s.getID(),s.getSubID()); return true;}
if(ls!=null) if(ls.getID()==s.getID() && ls.getSubID()==s.getSubID())
{if(ls.getStatus()<s.getStatus()) {ls=s; return true; }}
return false;
} public void listen(Object o)
{if(!(o instanceof Message)) return; Message m=(Message)o;
if(!(m.getObject() instanceof LightStatus)) return;
LightStatus s=(LightStatus)m.getObject();
if(update(s))
{echo(); if(time==-1) new Thread(this).start();
setChanged(); notifyObservers();
}
} private void echo()
{EchoLight el=new EchoLight(ml.getSeat(),ls.getStatus());
Message m=input.createMessage(el);
int p=ls.getTableID()+Receiver.TABPORT;
Tools.sendThing(m,input.getServer(),p,input.getSocket());
}
public void confirm(boolean r)
{if(ls==null) return;
if(ls.getID()!=ml.getID() || ls.getSubID()!=ml.getSubID()) return;
if(!Color.yellow.equals(ml.getLight())) return;
if(r) ml.setLight(Color.green); else ml.setLight(Color.red);
repeat(); //setChanged(); notifyObservers();
} private void repeat()
{if(ls==null) return;
if(ml.getLight().equals(Color.yellow)) return;
if(ml.getLight().equals(ls.getLight(ml.getSeat()))) return;
Message m=input.createMessage(ml);
int p=Receiver.TABPORT+ls.getTableID();
Tools.sendThing(m,input.getServer(),p,input.getSocket());
}
public void run()
{time=0; while(true) //flag=true; true if running
{try {Thread.sleep(1000);}
catch(Exception e) {System.out.println(e.toString());}
time++; setChanged(); notifyObservers();
if(time==MAXTIME || ls.getFlag()==false) break; repeat();
}
time=-1; setChanged(); notifyObservers();
}
}
还是您找个美化器……偶的程序的目的是让几个客户确认一下(点击“是”),服务器把结果随时反馈给客户
假定相互知道IP和端口,使用UDP,需实现重发和确认
就这么看似简单的功能,也折腾了好多时间以下帖一个服务器端的类package server;import java.net.*;
import java.awt.Color;import link.*;
import guai.GuaiType;
import guai.GuaiState;
import table.*;public class Confirmer
{public static final int MAXTIME=15,ENDED=-1;
LightStatus lights; Client list[]; int time;
public Confirmer()
{lights=new LightStatus(); time=-1;} //ge=new GuaiEngine(tab); tab=t;
public void reset(int n) {lights.reset(n); time=0;}
public void setClients(Client c[]) {list=c;}
public void prepare(long id,int t1,int t2) {lights.prepare(id,t1,t2);}
public int getTime() {return time;}
public LightStatus getLights() {return lights; }
public void processLight(MyLight ml)
{
if(Color.green.equals(ml.getLight()))
{lights.setGreen(ml.getSeat());
if(lights.getCounter()==list.length)
{time=ENDED;System.out.println("OKgreen");}// { new Thread(ge).start(); }
} if(Color.red.equals(ml.getLight()))
{lights.setRed(ml.getSeat()); time=ENDED;}
}
public synchronized boolean finished()
{if(time==ENDED || lights.getFlag()==false) return true; return false;}
public synchronized void tick()
{if(time==ENDED) return;
time++; if(time==MAXTIME) time=ENDED;
// {for(int i=0;i<list.length;i++)
// {if(!Color.green.equals(lights.getLight(i))) {;} }//tab.removeUser(i);
// }
}
}
import java.awt.Color;public class LightStatus implements Serializable
{long id; int tabid,subid,status,total,counter; Color lights[]; boolean flag;
public LightStatus()
{lights=new Color[Table.MAXPLAYERS]; }
public long getID() {return id;}
public int getTableID() {return tabid;}
public int getSubID() {return subid;}
public int getCounter() {return counter;}
public int getStatus() {return status;}
public int getTotal() {return total;}
public synchronized void setGreen(int n)
{lights[n]=Color.green; counter++; status++; if(counter==total) flag=false;}
public synchronized void setRed(int n)
{lights[n]=Color.red; status++; flag=false;}
public synchronized Color getLight(int n)
{if(n<0 || n>lights.length-1) return null; return lights[n]; }
public Color [] getLights() {return lights;}
public boolean getFlag() {return flag;}
public void prepare(long i,int t1,int t2) {id=i; tabid=t1; total=t2;}
public void reset(int n)
{subid=n; status=0; counter=0; flag=true;
for(int i=0;i<total;i++) lights[i]=Color.yellow;
} public void print()
{for(int i=0;i<total;i++)
{System.out.println(i+")"+lights[i].toString()); }
}
}
没必要把setVisible(false)改成dispose()
看来还是偶的错?但偶还是没明白是怎么错的
但是从4楼的运行输出看,setVisible(false)之后应该没有setVisible(true)
多个线程的运行顺序超出偶的想象?
其实偶还是没明白到底错在哪里
偶只有使用最最严格的逻辑、编写最最正确的代码,方能取得想要的结果以下帖的是更正确的Confirmee类,感谢各位的关注和支持!
package table;import java.util.*;
import java.io.Serializable;
import java.awt.Color;
import java.awt.*;import link.*;
import guai.GuaiType;
//import guai.GuaiEngine;public class Confirmee extends Observable implements Runnable,Listener
{public static final int MAXTIME=20;
Receiver2 input; MyLight ml; LightStatus ls; int time; //boolean flag;
public static void main(String args[])
{if(args.length!=1) {System.out.println("One Arg Pls!"); return;}
int n;
try
{n=Integer.parseInt(args[0]); System.out.println("No."+n+" Client");
Receiver2 r=new Receiver2(n); Confirmee cf=new Confirmee(r);
cf.setSeat(n);
Frame f=new Frame(); ConfirmDialog cd=new ConfirmDialog(f,cf);
}
catch(Exception e) {System.out.println(e.toString());}
} public Confirmee(Receiver2 r)
{input=r; input.addListener(this); ml=new MyLight(); ls=null; time=-1;} public MyLight getMyLight() {return ml;}
public LightStatus getLightStatus() {return ls;}
public Color [] getLights() {return ls.getLights();}
public int getSeat() {return ml.getSeat();}
public void setSeat(int s) {ml.setSeat(s);}
public int getTime() {return time;}
// public int getTimeout() {return MAXTIME-time;} private boolean update(LightStatus s)
{
if(ls==null)
{ls=s; ml.reset(s.getID(),s.getSubID()); new Thread(this).start(); return true;}
if(ls!=null) if(ls.getID()<s.getID())
{ls=s; ml.reset(s.getID(),s.getSubID()); new Thread(this).start(); return true;}
if(ls!=null) if(ls.getID()==s.getID() && ls.getSubID()<s.getSubID())
{ls=s; ml.reset(s.getID(),s.getSubID()); new Thread(this).start(); return true;}
if(ls!=null) if(ls.getID()==s.getID() && ls.getSubID()==s.getSubID())
{if(ls.getStatus()<s.getStatus()) {ls=s; return true; }}
return false;
} public void listen(Object o)
{if(!(o instanceof Message)) return; Message m=(Message)o;
if(!(m.getObject() instanceof LightStatus)) return;
LightStatus s=(LightStatus)m.getObject();
if(update(s)) {echo(); }
} private void echo()
{Echo el=new Echo(ml.getSeat(),ls.getStatus());
Message m=input.createMessage(el);
int p=ls.getTableID()+Receiver.TABPORT;
Tools.sendThing(m,input.getServer(),p,input.getSocket());
}
public void confirm(boolean r)
{if(ls==null) return;
if(ls.getID()!=ml.getID() || ls.getSubID()!=ml.getSubID()) return;
if(!Color.yellow.equals(ml.getLight())) return;
if(r) ml.setLight(Color.green); else ml.setLight(Color.red);
repeat(); //setChanged(); notifyObservers();
} private void repeat()
{if(ls==null) return;
if(ml.getLight().equals(Color.yellow)) return;
if(ml.getLight().equals(ls.getLight(ml.getSeat()))) return;
Message m=input.createMessage(ml);
int p=Receiver.TABPORT+ls.getTableID();
Tools.sendThing(m,input.getServer(),p,input.getSocket());
}
public void run()
{time=0; setChanged(); notifyObservers();
while(true) //flag=true; true if running
{try {Thread.sleep(1000);}
catch(Exception e) {System.out.println(e.toString());}
time++; setChanged(); notifyObservers();
if(time==MAXTIME || ls.getFlag()==false) break; repeat();
}
time=-1; setChanged(); notifyObservers();
}
}