0

我序列化了一些对象,所以我可以将它们转换为TCP数据包的字节数组。当我将服务器程序中的对象发送到客户端程序时,没有问题,并且工作正常。但是,即使服务器和客户端之间的代码是相同的,但当我尝试从客户端向服务器发送对象时,我会收到无效的标头。客户端到服务器的流头434B0005无效

这里是我的序列化对象:

public static byte[] serialize(Hand c) throws IOException 
    { 
     ByteArrayOutputStream baos = new ByteArrayOutputStream(); 
     ObjectOutputStream oos = new ObjectOutputStream(baos); 
     oos.writeObject(c); 
     return baos.toByteArray(); 
    } 

    public static Hand deserialize(byte[] bytes) throws IOException, ClassNotFoundException 
    { 
     ByteArrayInputStream b = new ByteArrayInputStream(bytes); 
     ObjectInputStream o = new ObjectInputStream(b); 
     return (Hand) o.readObject(); 
    } 

public static byte[] serialize(Card c) throws IOException 
    { 
     ByteArrayOutputStream baos = new ByteArrayOutputStream(); 
     ObjectOutputStream oos = new ObjectOutputStream(baos); 
     oos.writeObject(c); 
     return baos.toByteArray(); 
    } 

    public static Card deserialize(byte[] bytes) throws IOException, ClassNotFoundException 
    { 
     ByteArrayInputStream b = new ByteArrayInputStream(bytes); 
     ObjectInputStream o = new ObjectInputStream(b); 
     return (Card) o.readObject(); 
    } 

这些都是从服务器程序采取的,但是对于序列化的代码是在服务器和之间是相同的客户;我非常重视从服务器到客户端的Card类和Hand类,以确保不会发生类似这样的错误。

服务器可以将Card或Hand转换为byte [],并通过DataOutputStream将其写入客户端,客户端可以通过DataInputStream接收Card或Hand,将其反序列化,并且读取没有问题。当我尝试从客户卡或手发送到服务器,但是,很少它的工作原理,通常我得到一个

Exception in thread "main" java.io.StreamCorruptedException: invalid stream header: 434B0005 
    at java.io.ObjectInputStream.readStreamHeader(Unknown Source) 
    at java.io.ObjectInputStream.<init>(Unknown Source) 
    at Hand.deserialize(Hand.java:29) 
    at KoiKoi_TCP_Server.takeClientTurn(KoiKoi_TCP_Server.java:321) 
    at KoiKoi_TCP_Server.main(KoiKoi_TCP_Server.java:380) 

其中Hand.java.29点,线

 ObjectInputStream o = new ObjectInputStream(b); 

手中的反序列化方法。

我明白它告诉我头部无效。我不知道如何解决它,因为它只打破了一个方向,代码是相同的。建议?

我一次只能发送一个孤立的对象,所以我不初始化多ObjectInputStreams或任何东西。

回答

1

我不初始化多ObjectOutputStreams或任何东西。

是的,你是。您正在为每个对象初始化一个新的ObjectOutputStream,然后给自己一个额外的问题,即需要知道要读取多少个字节才能接收每个对象,并且您遇到了错误,所以您会失去同步。

摆脱所有这些。你不需要它。这只是增加了问题。只需使用一个ObjectOutputStream和ObjectInputStream,直接在套接字的生命周期中构建,直接在套接字流上构建,并在您想要发送对象时调用writeObject(),并在读取对象时调用readObject()。两行代码。忘掉字节数组和ByteArray/DataInput/OutputStreams。

+0

我会调整代码以反映您的建议,看看是否有效。你能澄清为什么它只能打破一个方向吗?你指出我得到的字节数是我需要读错的,这让我不知何故失去同步;如果可以从我发布的代码中收集这些信息,会导致什么结果? – 2013-03-11 03:44:46

+0

以某种方式解决同步问题是唯一合理的解释。我不知道'走向一个方向'是什么意思,但是代码不必有100%的错误率。 – EJP 2013-03-11 04:41:00

相关问题