【问题标题】:How to stop Getting streamcurrupted exception in writing object second time in Java Sockets如何在 Java Sockets 中第二次写入对象时停止获取流损坏异常
【发布时间】:2013-01-23 18:23:23
【问题描述】:

当我尝试从服务器获取对象时,我在客户端收到了 streamCorruptedException。

一开始当客户端连接到服务器时它运行良好,但是当我尝试连接第二个客户端或第二次运行时,出现错误。我也尝试在服务器端重置流,但它没有奏效。 已编辑:

以下是我的SERVER代码:

       Socket clientSocket=null;
            BufferedReader rdr=null;
            ObjectOutputStream objwriter=null;
            String name="";
            audioReceiver = new TAudioReceiver(ser);
            videoReceiver = new TVideoReceiver(ser);
            fileReceiver = new TFileReceiver(ser);
            //audioReceiver.start();
            //videoReceiver.start();
            //fileReceiver.start();
            InputStream cliIn=null;
            OutputStream cliOut = null;
            ClientDetails client=null;


            while(true)
            {
                objwriter=null;
                clientSocket = ser.MainSocket().accept();
                cliIn = clientSocket.getInputStream();
                cliOut = clientSocket.getOutputStream();
                client = new ClientDetails(clientSocket);
                rdr= new BufferedReader( new InputStreamReader(cliIn));
                name = rdr.readLine();
                System.out.println("Client connected '"+ name +"'");

                boolean a = ser.clientsMainSockets.AddClient(name, client);
                if(a){
                    ser.clientsNames = ser.clientsMainSockets.ClientNames();

                    wr = new BufferedWriter(new OutputStreamWriter(cliOut));
                    wr.write("OKM");
                    wr.write('\n');
                    wr.flush();
                    objwriter = new ObjectOutputStream(cliOut);
                    //Thread.sleep(1000);
                    objwriter.writeObject(ser.clientsNames);
                    objwriter.flush();
                    clientSocket =null;
                    cliIn = null;
                    cliOut = null;

                    client = ser.clientsMainSockets.Value(name);

                    TMessageHandler msghdl = new TMessageHandler(ser, client.InputStream() , client.OutputStream(), name);
                    clientHandler.add(msghdl);
                    msghdl.start();
                    System.out.println("Starting process for client");
                    objwriter.reset();
                    Thread.sleep(5000);
                }
                else{

                        wr = new BufferedWriter(new OutputStreamWriter(cliOut));
                        wr.write("ERROR");
                        wr.write('\n');
                        wr.flush();
                }


            }
    }
    catch(Exception ex)
    {
    }

以下是客户端代码:

 mainSock = new Socket(serverIp,serMainPort);
            serOut = mainSock.getOutputStream();
            serIn = mainSock.getInputStream();
            buffWr= new BufferedWriter(new OutputStreamWriter(serOut));
            //serOut = mainSock.getOutputStream();
            //serIn = mainSock.getInputStream();
            buffWr.write(myName);
            buffWr.write('\n');
            buffWr.flush();
            buffRdr = new BufferedReader(new InputStreamReader(serIn));
            String per="";
            per = buffRdr.readLine();
            System.out.println(per);
            if(per.equals("OKM"))
            {

                objin = new ObjectInputStream(serIn);
                ClientsName = (String[])objin.readObject();
                System.out.println("Client no.'"+ ClientsName.length );
                msgHandler = new TMainHandler(this, serOut, serIn);
                msgHandler.start();
            }
            else {
                throw new Exception("User Already exisits. Choose Another name.");
            }
        }
        catch(Exception ex)
        {
            throw new Exception(ex.getMessage());
        }

【问题讨论】:

  • 那些 sleep() 调用实际上是在浪费时间。
  • 我怀疑他们在那里模拟数据包或不同流之间的中断。确实,它们是不需要的工作。

标签: java sockets exception stream


【解决方案1】:

您不应该混合使用文本流和二进制流,因为这通常会导致混淆,除非您真的知道自己在做什么。

我建议您将 mainSock.getInputStream() 和 mainSocket.getOutputStream() 包装一次以用于流的生命周期,并且仅使用它。即不要多次调用它。

【讨论】:

  • 请看一下,我已经改了但是还是一样的错误。
  • 您仍在不止一个地方包装它。您需要决定如何包装它并只执行一次。
  • 实际上在 server 中,这是一个线程,它将接收一个客户端并启动另一个线程,通过将这些流发送到其中的子线程来与该客户端一起工作。然后循环将重新开始并接收这些流发送到子线程,你能解释一下我该怎么做吗,谢谢
  • 我只会将套接字传递给子线程,在这种情况发生之前不对套接字做任何事情。这样就没有流可以通过。然后创建两个流,一个用于输入,一个用于输出,并且您只使用这些流。
  • 顺便说一句,我怀疑你正在使用睡眠来让你的程序工作。这是一个坏主意,因为它不可靠。相反,您应该编写代码以便不需要延迟。
猜你喜欢
  • 1970-01-01
  • 2016-01-10
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-09-04
  • 2020-09-17
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多