2012-01-06 119 views
34

所以,我試圖讓我的機器在我的本地網絡(應該是192.168.178.41)的IP地址。獲取本地IP地址而無需連接到互聯網

我的第一個目的是使用這樣的:

InetAddress.getLocalHost().getHostAddress(); 

但它只返回127.0.0.1,這是正確的,但不適合我很大的幫助。

我尋找了一圈,發現這個答案https://stackoverflow.com/a/2381398/717341,它只是創建了一個Socket -connection一些網頁(如「google.com」),並得到從插座本地主機地址:

Socket s = new Socket("google.com", 80); 
System.out.println(s.getLocalAddress().getHostAddress()); 
s.close(); 

這對我的機器有效(它返回192.168.178.41),但它需要連接到互聯網才能工作。由於我的應用程序不需要互聯網連接,並且它可能看起來應用程序試圖在每次啓動時連接到谷歌的「可疑」,所以我不喜歡使用它的想法。

於是,經過一些調查研究我穿過NetworkInterface -class,(加上一些工作)不還返回所需的IP地址跌跌撞撞:

Enumeration<NetworkInterface> interfaces = NetworkInterface.getNetworkInterfaces(); 
while (interfaces.hasMoreElements()){ 
    NetworkInterface current = interfaces.nextElement(); 
    System.out.println(current); 
    if (!current.isUp() || current.isLoopback() || current.isVirtual()) continue; 
    Enumeration<InetAddress> addresses = current.getInetAddresses(); 
    while (addresses.hasMoreElements()){ 
     InetAddress current_addr = addresses.nextElement(); 
     if (current_addr.isLoopbackAddress()) continue; 
     System.out.println(current_addr.getHostAddress()); 
    } 
} 

在我的機器,這將返回以下:

name:eth1 (eth1) 
fe80:0:0:0:226:4aff:fe0d:592e%3 
192.168.178.41 
name:lo (lo) 

它找到我的網絡接口並返回所需的IP,但我不確定其他地址(fe80:0:0:0:226:4aff:fe0d:592e%3)是什麼意思。

此外,我還沒有找到一種方法來從返回的地址(通過使用isXX()-方法InetAddress-對象)過濾它,然後使用正則表達式,我發現它非常「髒」。

除了使用RegEx或互聯網以外的其他想法?

+2

FE80:0:0:0:226:4aff:fe0d:592e看起來像一個IPv6地址 – 2012-01-06 23:00:02

+0

'FE80 :: ...'是IPv6鏈路本地ADDRES s – fge 2012-01-06 23:00:15

+0

順便說一句,你想「過濾」什麼?當然,你知道一臺機器可以多宿主嗎? – fge 2012-01-06 23:02:01

回答

24

fe80:0:0:0:226:4aff:fe0d:592e是您的ipv6地址;-)。

入住此使用

if (current_addr instanceof Inet4Address) 
    System.out.println(current_addr.getHostAddress()); 
else if (current_addr instanceof Inet6Address) 
    System.out.println(current_addr.getHostAddress()); 

如果你只關心支持IPv4,然後就放棄了IPv6的情況。但要小心,IPv6是未來^^。

P.S .:檢查您的某些break應該是continue s。

+1

'getHostAddress()'出現在'InetAddress'基類中,不需要在這裏進行轉換(http://docs.oracle.com/javase/6/docs/api/java/net/InetAddress.html#getHostAddress ()) – skaffman 2012-01-06 23:13:44

+0

這看起來不錯,它的作品。雖然只是爲了過濾它們,但不需要劇組。我知道IPv6是未來,但對於我目前的需求,IPv4可以做得很好;-)當然,你對「break」是正確的。我糾正了這一點。謝謝,直到這裏! – 2012-01-06 23:15:37

+0

@skaffman:採取的點 - 被刪除 – yankee 2012-01-06 23:37:54

2

Yankee的答案對第一部分是正確的。要打印出來的IP地址,你可以把它作爲一個字節數組,將其轉換成正常的字符串表示這樣的:

StringBuilder ip = new StringBuilder(); 
for(byte b : current_addr.getAddress()) { 
    // The & here makes b convert like an unsigned byte - so, 255 instead of -1. 
    ip.append(b & 0xFF).append('.'); 
} 
ip.setLength(ip.length() - 1); // To remove the last '.' 
System.out.println(ip.toString()); 
+0

僅僅使用'current_addr.getHostAddress()'會有什麼優勢? – 2012-01-06 23:18:11

+0

@Lukas Knuth:起初我沒有在我的答案打印。我在一分鐘後將它們編輯爲帖子,因爲我認爲這可能相當有用;-)。羅素可能沒有看到那個版本。 – yankee 2012-01-06 23:40:09

+0

哎呀,我的壞 - 我認爲getHostAddress打印出了嚴格的正則表達式的全文。我沒有注意到當前的早期版畫。 – 2012-01-07 00:11:33

5
import java.net.*; 

public class Get_IP 
{ 
    public static void main(String args[]) 
    { 
     try 
     { 
      InetAddress addr = InetAddress.getLocalHost(); 
      String hostname = addr.getHostName(); 
      System.out.println(addr.getHostAddress()); 
      System.out.println(hostname); 
     }catch(UnknownHostException e) 
     { 
      //throw Exception 
     } 


    } 

}

+3

正如我上面提到的,這給你在Linux上的'127.0.0.1'。但是,這可能適用於Windows系統...... – 2012-02-01 18:19:25

+0

它首先被提及。 – Mavlarn 2013-12-17 01:37:53

8
public static String getIp(){ 
    String ipAddress = null; 
    Enumeration<NetworkInterface> net = null; 
    try { 
     net = NetworkInterface.getNetworkInterfaces(); 
    } catch (SocketException e) { 
     throw new RuntimeException(e); 
    } 

    while(net.hasMoreElements()){ 
     NetworkInterface element = net.nextElement(); 
     Enumeration<InetAddress> addresses = element.getInetAddresses(); 
     while (addresses.hasMoreElements()){ 
      InetAddress ip = addresses.nextElement(); 
      if (ip instanceof Inet4Address){ 

       if (ip.isSiteLocalAddress()){ 

        ipAddress = ip.getHostAddress(); 
       } 

      } 

     } 
    } 
    return ipAddress; 
} 
+0

此代碼將忽略Linux中的127.0.0.1 ip – 2013-09-22 15:41:47

+0

這與答案和我提供的內容有什麼不同? – 2013-09-22 16:21:15

+0

在你的代碼將返回127.0.0.1 – 2013-09-23 06:44:28

13

這裏也是一個java這樣做的8路:

public static String getIp() throws SocketException { 

    return Collections.list(NetworkInterface.getNetworkInterfaces()).stream() 
      .flatMap(i -> Collections.list(i.getInetAddresses()).stream()) 
      .filter(ip -> ip instanceof Inet4Address && ip.isSiteLocalAddress()) 
      .findFirst().orElseThrow(RuntimeException::new) 
      .getHostAddress(); 
} 
+1

這是唯一的解決方案,返回我的實際LAN IP地址。謝謝! – Pali 2015-12-07 19:54:04