2013-02-08 106 views
2

我正在使用Socket類進行java TCP連接。使用超時連接Socket.connect

Socket socket = new Socket(); 
socket.connect(new InetSocketAddress(host,port),50); 

我想這個連接建立得很快或根本沒有建立,所以我使用了50毫秒的連接超時時間。

但是,如果我測量這些調用之間的時間,我會得到超過50毫秒:125毫秒,甚至200毫秒。測量我使用System.currentMillis()的時間。我知道這種方法的粒度不是很好,但+ 100ms的差異只是荒謬的。

連接方法有問題嗎?超時時間太短了50毫秒?我在Windows 7上使用java 1.7.0_03。

+0

我不知道這是沒有實現的詳細知識交代。底層操作系統也可能使用特定的最小值或粒度作爲超時值。還要考慮從主機名解析IP地址所需的時間;這不是連接超時AFAIK的一部分。 – 2013-02-08 16:59:38

+2

您是在測量連接成功還是失敗? – 2013-02-08 17:00:51

+0

也可能只有第一次連接嘗試需要很長時間。嘗試在100個連接的循環中測量它。 – 2013-02-08 17:03:07

回答

0

在tdn120的answer上展開我最後搬了println。我始終如一地使用< 100.我也運行Windows 7,Java 7(1.7.0)。

javac -g SocketTest.java && java SocketTest localhost:80 abcd.com:80 localhost:80 localhost:80 localhost:80 
Testing: localhost:80 
java.net.SocketTimeoutException: connect timed out 
Time: 63 
Testing: abcd.com:80 
java.net.UnknownHostException: abcd.com 
Time: 2350 
Testing: localhost:80 
java.net.SocketTimeoutException: connect timed out 
Time: 50 
Testing: localhost:80 
java.net.SocketTimeoutException: connect timed out 
Time: 50 
Testing: localhost:80 
java.net.SocketTimeoutException: connect timed out 
Time: 50 

我的代碼如下:

import java.net.*; 

public class SocketTest { 
    public static void main(String[] args) throws Exception { 
     if (args.length == 0) { 
      args = new String[]{"localhost:80"}; 
     } 
     for (String target: args) { 
      test(target); 
     } 
    } 

    private static void test(String target) throws Exception { 
     System.out.println("Testing: " + target); 
     String[] parts = target.split(":"); 
     String host = parts[0]; 
     int port = Integer.valueOf(parts[1]); 
     Socket socket = new Socket(); 
     long start = 0; 
     try { 
      start = System.nanoTime(); 
      socket.connect(new InetSocketAddress(host, port), 50); 
     } catch (Exception e) { 
      System.out.println(e.toString()); 
     } finally { 
      long end = System.nanoTime(); 
      System.out.println("Time: " + ((end - start)/1000000)); 
     } 
    } 
} 
+0

是的,但這是我沒有得到的。在你的例子中,你得到了63和2350.爲什麼?我的意思是你說的方法你不想等待超過50毫秒,所以爲什麼需要更長的時間。高達2350!也許你傳遞給連接方法的超時只是一種建議... – 2013-02-09 00:55:04

+0

我希望你會注意到額外的時間。 50毫秒是套接字連接超時。當我使用名稱而不是i/p時,尤其是無效名稱(abcd.com)時,dns失敗需要更多時間。 – 2013-02-09 01:00:37

+0

在完成socket.close()操作後,我正在測量finally子句中的總時間。它似乎需要很多時間:( – 2013-02-10 19:42:17

0

我有一種感覺,它與你如何計時有關。您需要確保您在執行之前和之後立即記錄時間。

雖然我使用Linux,我一直得到的51或52,此代碼的結果:

public class SocketTest { 
    public static void main(final String[] args) throws IOException { 
     Socket socket = new Socket(); 
     long start = 0; 
     try { 
      start = System.nanoTime(); 
      socket.connect(new InetSocketAddress("192.168.1.100", 80), 50); 
     } catch (SocketTimeoutException e) { 
      long end = System.nanoTime(); 
      System.out.println("Time: " + ((end - start)/1000000)); 
     } 
    } 
} 

更新:我試了一下在Windows 7中,我得到50的和51的。

+0

我完全按照您的測量時間(但使用currentMillis而不是nanoTime)。實際上,當我使用我的專用網絡中的主機時,我得到了50和51,但當我使用外部ips時卻沒有。 – 2013-02-09 00:48:34