用套接字交换对象

时间:2015-04-12 15:43:41

标签: java sockets serialization

我正在尝试使用套接字在Java中编写客户端和服务器之间的简单交互。

服务器

public class MyServer
{
  private static final int SPORT = 4444;
  ServerSocket server;
  Socket client;
  ObjectInputStream is;
  ObjectOutputStream os;


  /**
   * Constructor
   */
  public MyServer() {
    try
    {
      server = new ServerSocket(SPORT);
    }
    catch (IOException e)
    {
      e.printStackTrace();
    }

    listenAndReply();
  }


  public void listenAndReply()
  {
    System.out.println("Server running.");
    System.out.println("Waiting for connection...");
    try
    {
      client = server.accept();

      System.out.println("Connection accepted. \n");

      is = new ObjectInputStream(client.getInputStream());
      os = new ObjectOutputStream(client.getOutputStream());

      while(! client.isClosed()) {

        Object o = is.readObject();

        // ... process object ...

      }
    }
    catch (IOException | ClassNotFoundException e)
    {
      e.printStackTrace();
    }
  }


  public void sendCommand(Command c) {
    try
    {
      os.reset();
      os.writeObject(c);
      os.flush();
    }
    catch (IOException e)
    {
      e.printStackTrace();
    }
  }

客户端

public class MyClient implements ChatClient
{
  private static final int SPORT    = 4444;
  private static final String SHOST = "127.0.0.1";
  Socket socket;
  ObjectInputStream is = null;
  ObjectOutputStream os = null;


  public MyClient() {
    try
    {
      socket = new Socket(SHOST, SPORT);
      os = new ObjectOutputStream(socket.getOutputStream());
      is = new ObjectInputStream(socket.getInputStream());
      System.out.println("Client socket created.");
    }
    catch (Exception e)
    {
      e.printStackTrace();
    }
  }


  @Override
  public Command receive()
  {
    try
    {
      Object o = is.readObject();

      if(o instanceof Command) {
        System.out.println("Received command: " + o.getClass().getSimpleName());
        return (Command) o;
      }
    }
    catch (IOException | ClassNotFoundException e)
    {
      e.printStackTrace();
    }

    return null;
  }


public void sendCommand(Command c) {
    System.out.println("Client sending command " + c.getClass().getSimpleName());

    try
    {
      os.reset();
      os.writeObject(c);
      os.flush();
      System.out.println("Command sent. \n");
    }
    catch (IOException e)
    {
      e.printStackTrace();
    }
  }

}
你能看到什么问题吗?问题是,如果我尝试交换多个对象,我会得到

java.io.StreamCorruptedException:类型代码无效:00

编辑 - 已解决

最后我设法解决了这个问题:正如Pshemo所怀疑的那样,问题不在于此代码中,而是在另一个类中,其他调用了receive方法,这显然会导致奇怪的行为。现在我将不得不重新考虑一下结构,但至少套接字通信似乎没问题。

1 个答案:

答案 0 :(得分:-1)

在服务器类中,您尝试从客户端获取输入和输出,但在您的客户端类中,您将tour客户端套接字设置为套接字而不是客户端。你试图通过类而不是套接字来提取信息,所以我猜这是你的问题。如果我错了,请纠正我

public class MyServer{

private static final int SPORT = 4444;



/**
* Constructor
*/
public MyServer() {
try
{
  ServerSocket server = new ServerSocket(SPORT);
}
catch (IOException e)
{
  e.printStackTrace();
}

listenAndReply();
}


public void listenAndReply(){

System.out.println("Server running.");
System.out.println("Waiting for connection...");
try
{
  socket = server.accept();

  System.out.println("Connection accepted. \n");

  InputStream is = new InputStream(socket.getInputStream()); //changed from client.getInputStream() because in your client class you have setup your client socket to be named socket instead of client.
  OutputStream os = new OutputStream(socket.getOutputStream()); //changed from client.getOutputStream() since your client class has a differently named client socket, your server can’t get information from it by calling client.get

  while( !socket.isClosed()) {

    Object o = is.readObject();

    // ... process object ...

  }
}
catch (IOException | ClassNotFoundException e)
{
  e.printStackTrace();
}

}