您好,并提前感谢您的帮助。我目前正在编写一款游戏,可以选择RMI或套接字作为从服务器到客户端进行通信的方式。现在,我目前在套接字实现方面遇到了一些问题。我通过流从客户端向服务器发送一个对象来定义游戏的某些参数的配置,服务器接收它并将其发送回客户端,但有时客户端碰巧收到空指针(有时候它有效,有时它不会。)
public class SocketClientListener implements Runnable {
private static final Logger log = Logger.getLogger(ClientCli.class.getName());
private ClientSocket cs;
private Scanner socketIn;
private PrintWriter socketOut;
private ObjectInputStream ois;
SocketClientListener(ClientSocket cs) {
this.cs = cs;
socketIn = this.cs.giveMeSocketIn();
socketOut = this.cs.giveMeSocketOut();
ois = this.cs.giveMeOis();
System.out.println("ois: " + ois);
}
@Override
public void run() {
boolean end = false;
String what;
while (!end) {
what = socketIn.next();
System.out.println(what + " MESS RECEIVED");
switch (what) {
case Constant.GIVECONFIG:// TODO
this.cs.setNeedsconfig(true);
this.cs.setStatusChanged(true);
break;
case "end":
this.cs.setEnd(true);
break;
case "updateconfig":
try {
Configuration c = (Configuration) ois.readObject();
this.cs.setConfig(c);
this.cs.setIdmatch(socketIn.nextInt());
socketIn.nextLine();// discarding a separator
this.cs.setStatus(Constant.WAITINGFORPLAYERS);
this.cs.setStatusChanged(true);
} catch (ClassNotFoundException | IOException e) {
log.log(Level.SEVERE, "Error updating match stats", e);
}
break;
case "updatematch":
try {// TODO streamcorrupted
boolean fail = true;
Match m = null;
while (fail) {
try {
m = (Match) ois.readObject();
fail = false;
boolean b = true;
socketOut.print(b);
socketOut.flush();
} catch (StreamCorruptedException e) {
boolean b = false;
socketOut.print(b);
socketOut.flush();
}
}
this.cs.setMatch(m);
System.out.println("match " + m);
} catch (ClassNotFoundException | IOException e) {
log.log(Level.SEVERE, "Error updating match", e);
}
this.cs.setStatus(Constant.STARTED);
this.cs.setStatusChanged(true);
break;
default:
this.cs.setResult(what);
this.cs.setResultsetted(true);
break;
}
}
}
}
这是从客户端创建的类线程的代码,该线程具有侦听从服务器接收的消息的作业,异常被抛出
Configuration c = (Configuration) ois.readObject();
和
m = (Match) ois.readObject();
这是从服务器创建的类线程,用于处理来自客户端的调用
public class SocketListener implements Runnable {
private boolean stop = false;
private Socket sock;
private Scanner inSocket;
private PrintWriter outSocket;
private Server server;
private String playername;
private boolean configurator = false;
ObjectOutputStream outToClient;
ObjectInputStream inFromClient;
SocketListener(Server server, Socket sock) throws UnknownHostException, IOException {
this.sock = sock;
this.server = server;
this.outToClient = new ObjectOutputStream(sock.getOutputStream());
this.inFromClient = new ObjectInputStream(sock.getInputStream());
}
使用这些方法与客户端通信并向他发送对象
public void updateConfig(Configuration c, int matchid) throws IOException {
this.outSocket.println("updateconfig");
this.outToClient.writeObject(c);
this.outToClient.flush();
this.outSocket.println(matchid);
this.outSocket.println(Constant.SUCCESS);
}
public void updateMatch(Match m) throws IOException {
this.outSocket.print("updatematch\n");
this.outSocket.flush();
this.outToClient.writeObject(m);
this.outToClient.flush();
boolean message;
if(this.inSocket.hasNextBoolean()){
System.out.println("yes");
message= this.inSocket.nextBoolean();
}
else{
System.out.println("no");
message=false;
}
while(!message){
System.out.println("FAILED");
this.outToClient.writeObject(m);
this.outToClient.flush();
message= this.inSocket.nextBoolean();
}
}
请注意,UpdateMatch方法比应该更复杂,因为添加了一个布尔值,应该作为控件接收,以查看我们发送的对象是否在
处抛出indexOutofBoundExceptionthis.inSocket.hasNextBoolean()
但在布尔控件之前,该方法在客户端代码中的readobject方法上抛出了StreamCorruptedException
有什么建议吗?再次感谢您的帮助