ArrayList不会通过套接字更新内容

时间:2014-04-13 16:04:34

标签: java multithreading sockets debugging arraylist

我有一个典型的多线程服务器和一个客户端,它通过套接字与服务器连接并进行一些操作。

客户端部分:

try {
        mySocket=new Socket("localhost", 1234);


    ObjectOutputStream oos= new ObjectOutputStream(mySocket.getOutputStream());  
    ObjectInputStream  ois= new ObjectInputStream(mySocket.getInputStream());


           try{
               while(true){

               //Here user is asked for input the protocol string  

                    if("one message".equals(protocol))                             
                       {   
                        oos.writeObject(protocol); 
                        oos.flush();

                        mylist=(ArrayList<MyClass>)ois.readObject();
                        System.out.println(mylist);
                       }


                    if("two message".equals(protocol))  
                        { 
                          //tell server to change few things    on the list                                               
                        }

}//end while        
        } //end inner try
                    catch (IOException | ClassNotFoundException ex)
                    {
                        // ex.printStackTrace();
                    }

            ois.close();
            oos.close();
            mySocket.close();

}//end outer try 
        catch (IOException e)
    {
        //message
    } 

服务器端:

public void run() {
try{

    ObjectInputStream ois = new ObjectInputStream(socket.getInputStream());               
    ObjectOutputStream oos = new ObjectOutputStream(socket.getOutputStream());  

    String protocol;


  try{

  while(true)
    {            
        protocol= (String)ois.readObject();


    if ("one message".equals(protocol))
            {                                
             oos.writeObject(list); 
             oos.flush();

             System.out.println(list);
         }


     if ("two message".equals(protocol))

    {
      //change objects in the list          
    }



} //end while true

    } //end try
                catch (IOException | ClassNotFoundException ex)
                {                        
                   // ex.printStackTrace();
                }

            ois.close();
            oos.close();
            socket.close();
}  
  catch (Exception ex)
            {                   
                //ex.printStackTrace();
            }
}

有问题的部分在这里:

if ("one message".equals(protocol))
                {

                 oos.writeObject(list); //sends the wrong (?)
                 oos.flush();

                 System.out.println(list); //prints the correct
             }

服务器从侧面看,似乎每次用户更改时都会打印正确的列表。但是,无论客户进行多少更改,客户都会收到并打印第一个列表。如果另一个线程出现并要求列表,它将采用最新列表,如果该线程或其他线程进行更多更改,服务器仍将每次从其侧面打印正确的列表,但客户端将始终返回错误的列表,这是该客户端线程进入时存在的列表。

2 个答案:

答案 0 :(得分:1)

ObjectOutputStream,如果您要求它发送已发送的对象,只需发送对先前发送的对象的引用。这允许发送对象的复杂图形,具有双向引用或对象之间的循环。

如果您希望流忘记已发送的内容,则需要调用reset()方法。

答案 1 :(得分:0)

您是序列化流中对象缓存的受害者。第一次编写对象时,正在为该参考地址创建缓存版本。然后每次你写它(即使你改变内容)它不再写它,因为它说“我已经看起来像这个地址的对象”。

解决此问题的最佳方法是将套接字流保留在while循环之外,但将ObjectOutput和ObjectInput流放在while循环中。这应该可以解决您的问题。通常,其中一组是针对一个稳定对象图设计的。