2014-07-14 274 views
0

我使用DataOutputStream在網絡上這樣的傳輸數據:等待套接字數據傳輸

Socket socket = new Socket(ipAddress, port); 
DataOutputStream dataOutputStream = new DataOutputStream(
        socket.getOutputStream()); 

dataOutputStream.writeBytes("Stackoverflow"); 
// ... 
System.exit(0); 

如果我的應用程序終止太早,傳輸將被中止,因此失敗,因爲不是所有的數據都有在那時已經發送。

爲了解決這個問題,我可以手動等待一段時間終止前:

try 
{ 
    Thread.sleep(1000); 
} catch (InterruptedException e) 
{ 
    e.printStackTrace(); 
} 

然而,這種解決方案是壞的。在終止我的應用程序之前,是否有一些確保所有數據已經​​發送的「最佳實踐」方法?

編輯:
我無權訪問服務器代碼。

+0

在網絡代碼中添加睡眠並不能完成任何操作。只要您正確關閉插座,數據就會到達。你確定問題不在另一端嗎? – EJP

+0

問題可能確實存在於另一端,但仍可能有解決此問題的方法。 – BullyWiiPlaza

回答

0

默認情況下,socket.close()應導致正常的TCP連接關閉。在該過程中,TCP堆棧將未確認的數據傳送給對等體。

dataOutputStream.flush(); 
socket.close(); 

如果您已將SO_LINGER設置爲零,則不起作用。 替代方案是使用socket.shutdownOutput()

dataOutputStream.flush(); 
socket.shutdownOutput(); 
+0

這兩個建議都不起作用,它仍然停止太早 – BullyWiiPlaza

+0

奇怪。你確定當你調用flush()時TCP連接仍然打開嗎?並且所有的數據已經寫入dataOutputStream? – SKi

+0

是的。我嘗試調用'socket.close()'和'socket.shutdownOutput()',就像您在所有'DataOutputStream'寫入後提示的一樣,但都未能等到所有內容都發送完畢。 – BullyWiiPlaza

1

如果我的應用程序終止太早,傳輸將被中止,因此自()不是所有的數據已發送尚未沖洗的執行後失效。

數據是無緩衝的,因此每次寫入都立即發送數據。在你的情況下,flush()沒有做任何事情。

DataOutputStream.flush()

public void flush() throws IOException { 
    out.flush(); 
} 

調用OutputStream.flush()

public void flush() throws IOException { 
} 

是否有確保所有數據已終止前已發送的一些 「最佳實踐」 的方式我應用?

確保數據已發送的最佳方式是等待答覆。讓另一端發回一條消息說它已收到它,並且您可以知道已收到數據。

順便說一句當你完成一個可關閉的資源時,最好的做法是關閉它。

+0

是的,我認爲'flush()'也沒有做什麼。問題在於我不知道如何訪問服務器代碼。我不確定我的套接字是否已經強制使用tcp連接。關於代碼的任何提示我都應該嘗試? – BullyWiiPlaza

+0

@ user3764804我認爲您需要更好地理解問題,因爲您的寫入應該發送數據,並且不需要使用close(),但它可以確保不再需要它。 –

相關問題