當前位置:編程學習大全網 - 編程語言 - Java Socket重要參數講解

Java Socket重要參數講解

 Java Socket的api可能很多人會用 但是Java Socket的參數可能很多人都不知道用來幹嘛的 甚至都不知道有這些參數

 backlog

 用於ServerSocket 配置ServerSocket的最大客戶端等待隊列 等待隊列的意思 先看下面代碼

 public class Main { public static void main(String[] args) throws Exception { int port = int backlog = ServerSocket serverSocket = new ServerSocket(port backlog) Socket clientSock = serverSocket accept() System out println( revcive from + clientSock getPort()) while (true) { byte buf[] = new byte[ ] int len = clientSock getInputStream() read(buf) System out println(new String(buf len)) }這段測試代碼在第壹次處理壹個客戶端時 就不會處理第二個客戶端 所以除了第壹個客戶端 其他客戶端就是等待隊列了 所以這個服務器最多可以同時連接 個客戶端 其中 個等待隊列 大家可以telnet localhost 測試下

 這個參數設置為 表示無限制 默認是 個最大等待隊列 如果設置無限制 那麽妳要小心了 如果妳服務器無法處理那麽多連接 那麽當很多客戶端連到妳的服務器時 每壹個TCP連接都會占用服務器的內存 最後會讓服務器崩潰的

 另外 就算妳設置了backlog為 如果妳的代碼中是壹直Socket clientSock = serverSocket accept() 假設我們的機器最多可以同時處理 個請求 總***有 個線程在運行 然後妳把在 個線程的線程池處理clientSock 不能處理的clientSock就排隊 最後clientSock越來越多 也意味著TCP連接越來越多 也意味著我們的服務器的內存使用越來越高(客戶端連接進程 肯定會發送數據過來 數據會保存到服務器端的TCP接收緩存區) 最後服務器就宕機了 所以如果妳不能處理那麽多請求 請不要循環無限制地調用serverSocket accept() 否則backlog也無法生效 如果真的請求過多 只會讓妳的服務器宕機(相信很多人都是這麽寫 要註意點)

 TcpNoDelay

 禁用納格算法 將數據立即發送出去 納格算法是以減少封包傳送量來增進TCP/IP網絡的效能 當我們調用下面代碼 如

 Socket socket = new Socket() nnect(new InetSocketAddress(host )) InputStream in = socket getInputStream() OutputStream out = socket getOutputStream() String head = hello String body = world\r\n out write(head getBytes()) out write(body getBytes()) 我們發送了hello 當hello沒有收到ack確認(TCP是可靠連接 發送的每壹個數據都要收到對方的壹個ack確認 否則就要重發)的時候 根據納格算法 world不會立馬發送 會等待 要麽等到ack確認(最多等 ms對方會發過來的) 要麽等到TCP緩沖區內容>=MSS 很明顯這裏沒有機會 我們寫了world後再也沒有寫數據了 所以只能等到hello的ack我們才會發送world 除非我們禁用納格算法 數據就會立即發送了

 SoLinger

 當我們調用socket close()返回時 socket已經write的數據未必已經發送到對方了 例如

 Socket socket = new Socket() nnect(new InetSocketAddress(host )) InputStream in = socket getInputStream() OutputStream out = socket getOutputStream() String head = hello String body = world\r\n out write(head getBytes()) out write(body getBytes()) socket close()

 這裏調用了socket close()返回時 hello和world未必已經成功發送到對方了 如果我們設置了linger而不小於 如

 bool on = true int linger = ……

 socket setSoLinger(boolean on int linger)

 ……

 socket close() 那麽close會等到發送的數據已經確認了才返回 但是如果對方宕機 超時 那麽會根據linger設定的時間返回

 UrgentData和OOBInline

 TCP的緊急指針 壹般都不建議使用 而且不同的TCP/IP實現 也不同 壹般說如果妳有緊急數據寧願再建立壹個新的TCP/IP連接發送數據 讓對方緊急處理

 所以這兩個參數 妳們可以忽略吧 想知道更多的 自己查下資料

 SoTimeout

 設置socket調用InputStream讀數據的超時時間 以毫秒為單位 如果超過這個時候 會拋出 SocketTimeoutException

 KeepAlive

 keepalive不是說TCP的常連接 當我們作為服務端 壹個客戶端連接上來 如果設置了keeplive為true 當對方沒有發送任何數據過來 超過壹個時間(看系統內核參數配置) 那麽我們這邊會發送壹個ack探測包發到對方 探測雙方的TCP/IP連接是否有效(對方可能斷點 斷網) 在Linux好像這個時間是 秒 如果不設置 那麽客戶端宕機時 服務器永遠也不知道客戶端宕機了 仍然保存這個失效的連接

 SendBufferSize和ReceiveBufferSize

 TCP發送緩存區和接收緩存區 默認是 壹般情況下足夠了 而且就算妳增加了發送緩存區 對方沒有增加它對應的接收緩沖 那麽在TCP三握手時 最後確定的最大發送窗口還是雙方最小的那個緩沖區 就算妳無視 發了更多的數據 那麽多出來的數據也會被丟棄 除非雙方都協商好

lishixinzhi/Article/program/Java/hx/201311/26575

  • 上一篇:軟件測試SQL面試問題
  • 下一篇:智利“法馬伊”沈底水雷
  • copyright 2024編程學習大全網