2010-03-06 66 views
26

Vấn đề của tôi là khi nó cố gắng để đọc các đối tượng lần thứ hai, nó ném ngoại lệ:StreamCorruptedException: Loại mã không hợp lệ: AC

java.io.StreamCorruptedException: invalid type code: AC 
    at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1356) 
    at java.io.ObjectInputStream.readObject(ObjectInputStream.java:351) 
    at Client.run(BaseStaInstance.java:313) 

java.io.StreamCorruptedException: invalid type code: AC 
    at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1356) 
    at java.io.ObjectInputStream.readObject(ObjectInputStream.java:351) 
    at Client.run(BaseStaInstance.java:313) 

Lần đầu tiên tôi gửi cùng một thông điệp đối tượng chính xác; tuy nhiên, khi tôi thử làm điều tương tự lần thứ hai, nó sẽ ném lỗi ở trên. Tôi có cần phải tái intialize phương thức readObject() không? Tôi thậm chí in ra các đối tượng tin nhắn đang được nhận bởi dòng dưới đây và chính xác của nó giống như trường hợp đầu tiên mà nó hoạt động ok.

Object buf = myInput.readObject(); 

Tôi giả sử có một số vấn đề với phụ thêm, nhưng tôi thực sự không sử dụng để thêm. Tôi chỉ muốn đọc một dòng mới mỗi lần. Tôi thực sự đánh giá cao một số trợ giúp trong việc sửa lỗi này. Cảm ơn bạn.

==================================

Trước đó một dòng, tôi chỉ cần tạo các đối tượng đầu vào và đầu ra cho socket trong phương thức run(). Khai báo đối tượng nằm ngoài phương thức run() trong lớp: -

@Override 
public void run() { 
    try { 
     sleep((int) 1 * 8000); 
    } catch (Exception e) { 
     e.printStackTrace(); 
    } 

    try { 
     //Creating input and output streams to transfer messages to the server 
     myOutput = new ObjectOutputStream(skt.getOutputStream()); 
     myInput = new ObjectInputStream(skt.getInputStream()); 
     while (true) { 
      buf = myInput.readObject(); 
     } 
    } catch (UnknownHostException e) { 
     e.printStackTrace(); 
    } catch (IOException e) { 
     e.printStackTrace(); 
    } finally { 
     try { 
     } catch (Exception e) { 
      e.printStackTrace(); 
     } 
    } 
} 

Bạn nói đúng; Tôi không đóng đối tượng. Tôi không chắc chắn làm thế nào để làm điều đó.

+0

Tôi không chắc chắn nơi để đóng đối tượng –

+0

NB Bạn nên bắt EOFException và không đối xử với nó dưới dạng lỗi: không đăng nhập hoặc in dấu vết ngăn xếp; chỉ để cho nó chấm dứt vòng lặp đọc. Tôi không biết tại sao bạn đang bắt UnknownHostException nơi bạn đang ở: nó không thể được ném từ bên trong khối thử tương ứng. Ngủ() chỉ là một sự lãng phí thời gian. Gỡ bỏ nó. – EJP

Trả lời

54

Vấn đề cơ bản là bạn đang sử dụng ObjectOutputStream mới để ghi vào ObjectInputStream hiện có mà bạn đã sử dụng trước ObjectOutputStream để ghi vào. Những dòng này có các tiêu đề được viết và đọc bởi các nhà xây dựng tương ứng, vì vậy nếu bạn tạo một số khác ObjectOutputStream, bạn sẽ viết một tiêu đề mới, bắt đầu bằng - đoán cái gì? - 0xAC, và hiện tại ObjectInputStream không mong đợi một tiêu đề khác tại thời điểm này để nó barfs.

Trong chuỗi diễn đàn Java được trích dẫn bởi @trashgod, tôi nên để lại phần về 'một lần nữa cho mỗi đối tượng ở cả hai đầu': đó chỉ là lãng phí. Sử dụng một OOS và OIS duy nhất cho tuổi thọ của ổ cắm và không sử dụng bất kỳ luồng nào khác trên ổ cắm.

Nếu bạn muốn quên những gì bạn đã viết, sử dụng ObjectOutputStream.reset().

Và đừng sử dụng bất kỳ con suối khác hoặc Readers hoặc Writers trên cùng một ổ cắm. API luồng đối tượng có thể xử lý tất cả các kiểu dữ liệu nguyên thủy Java và tất cả các lớp Serializable.

+1

+1 @rookie: Đây là câu trả lời đúng và từ nguồn gốc! :-) – trashgod

+0

@EJP evrytime i chạy mã OOS mới và OIS được tạo. làm thế nào để tôi quản lý điều đó? –

+0

@AkhilKNambiar Tôi không biết bạn đang hỏi tôi điều gì chưa được trả lời ở trên. – EJP

-1

Đối mặt một ngoại lệ tương tự khi sử dụng Java 7/8, tôi giải quyết nó bằng cách thêm dưới đây tranh luận VM

-Dsun.lang.ClassLoader.allowArraySyntax=true 
+0

'Tương tự' không giống nhau. Điều này không giải quyết vấn đề được đăng bởi OP. – EJP

Các vấn đề liên quan