java什么是网络接口_java 网络编程 -- IP地址的表示与网络接口信息的获取(InetAddress和NetworkInterface)...
使用java進行網絡程序的開發,可以說是一件令人愉悅的事情,對于用慣了C++網絡接口編程的人來說,當他們首次使用Java開發網絡應用程序,會發現java開發網絡應用是如此的簡單,甚至僅用幾分鐘時間,您就可以學會這種網絡編程技術。本章主要對java網絡編程相關的知識進行探討,首先探討java對于網卡信息獲取方式,之后介紹如何使用java編寫基于網絡的客戶端和服務端程序。最后探討一些java網絡相關的高級主題。
3.1 java獲取網絡通信信息
java為了方便網絡編程,提供了表示IP地址的類、表示網絡接口(這個接口是指網卡)的類,表示網絡連接接口的類。下面主要探討這些基本的類,以及如何使用這些類來獲取網絡信息。Graphic3-1給出了與網絡通信信息相關的類之間的關系。
Graphic3-1 網絡通信信息相關的類
3.1.1 InetAddress類
InetAddress用來表示一個IP地址。可以通過主機名來配置InetAddress,此時InetAddress將會通過主機配置的DNS服務器解析出對應域名的IP地址。對于任何的主機名,InetAddress也可以解析出其對應的IP地址。InetAddress擁有兩個子類,分別是Inet4Address和Inet6Address,在大多說情況下都無需直接處理這些子類,因為InetAddress抽象類已經覆蓋了大多數必需的功能。Graphic3-2給出了InetAddress的公有操作。從Graphic3-2從可以看出,InetAddress類沒有公有的構造方法,要想獲取InetAddress的實例必需使用InetAddress內部的一些靜態方法(這是設計模式中的簡單工廠方法)。
Demo3-1給出了使用InetAddress的基本用法。示例中先使用InetAddress的getLocalHost方法獲取了本機的IP地址,然后輸出,使用getByName方法獲得了google服務器的一個IP地址,由于google服務器有很多服務主機,當前獲取的是哪一個服務的主機的IP地址并不確定,實際應用中,這是一個隨機的值,這與DNS服務器有直接關系。使用了getByAllName方法可以獲取google的所有服務主機名。最后使用了isReachable方法來判斷一臺主機的可達性。
需要說明的是,使用getLocalHost方法未必真的能夠獲取您想要的本機的IP地址(有人說,在windows上getLocalHost可以正確執行,獲取到本機的IPV4地址,而在Linux上調用getLocalHost返回的是一個127.0.0.1的ip地址)。現在假想有一臺主機有多張網卡,而且有多個IP地址,甚至這臺主機即配置了IPV4又配置了IPV6,調用getLocalHost將會返回哪一個IP地址?很明顯getLocalHost只能返回一個IP地址,因此就限定了getLocalHost方法并不是獲取本機IP地址的最好方式。
Demo3-2給出了一臺Linux系統一張網卡上配置IPV4和IPV6后,調用getLocalHost后的執行結果。從Configuration3-2中可以看出,在這臺linux上配置了IPV4和IPV6,調用getLocalHost后,獲取的是一個回環測試地址。
此外,使用InetAddress的isReachable時需要特別小心,因為默認情況下,isReachable使用ICMP報文來探測遠程主機可達性(不一定使用ICMP,這與具體的實現有關),有很多服務器或者網絡管理員禁用ping功能(ICMP),所以使用isReachable不可達,并不證明遠程主機不存在。
Graphic3-2InetAddress擁有的公有操作。
Demo 3-1 InetAddress示例代碼
package com.upc.upcgrid.guan.network.chapter03;
import java.io.IOException;
import java.net.InetAddress;
public class InetAddressTest {
public static void main(String[] args) throws IOException {
InetAddress addr = InetAddress.getLocalHost();//獲取本機ip
System.out.println("local host : "+addr);
//獲取指定服務的一個主機IP
addr = InetAddress.getByName("google.com");
System.out.println("google : " + addr);
//獲取指定服務的所有主機IP
InetAddress[] addrs = InetAddress.getAllByName("google.com");
for(int i = 0 ;i < addrs.length ;i++)
System.out.println("google : "+addrs[i] + "number : " + i);
//獲取遠程主機可達性
System.out.println(InetAddress.getByName("localhost").isReachable(1000));
}
}
Demo3-1執行結果:
local host : PC2011022509cjh/202.194.158.128
google : google.com/74.125.71.99
google : google.com/74.125.71.99number : 0
google : google.com/74.125.71.103number : 1
google : google.com/74.125.71.104number : 2
google : google.com/74.125.71.105number : 3
google : google.com/74.125.71.106number : 4
google : google.com/74.125.71.147number : 5
true
demo3-1的配置:
configuration 3-1:windows主機的配置
C:\Documents and Settings\Administrator>ipconfig
Windows IP Configuration
Ethernet adapter 本地連接:
Connection-specific DNS Suffix. :
IP Address. . . . . . . . . . . . : 202.194.158.128
Subnet Mask . . . . . . . . . . . : 255.255.255.0
Default Gateway . . . . . . . . . : 202.194.158.253
Demo3-2 linux 執行的代碼:
System.out.println(InetAddress.getLocalHost());
Demo3-2 的輸出結果:
Localhost.localdomain/127.0.0.1
Demo3-2 的配置環境
Configuration 3-2 linux主機的配置
[root@localhost ~]# ifconfig
eth0Link encap:EthernetHWaddr 00:E0:4C:3D:C2:73
inet addr:202.194.158.184Bcast:202.194.158.255Mask:255.255.255.0
inet6 addr: 2001:da8:7006:8003:2e0:4cff:fe3d:c273/64 Scope:Global
inet6 addr: fe80::2e0:4cff:fe3d:c273/64 Scope:Link
UP BROADCAST RUNNING MULTICASTMTU:1500Metric:1
RX packets:251210956 errors:1 dropped:28 overruns:1 frame:0
TX packets:116140638 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:1000
RX bytes:16023749113 (14.9 GiB)TX bytes:34386034544 (32.0 GiB)
Interrupt:217 Base address:0x2000
loLink encap:Local Loopback
inet addr:127.0.0.1Mask:255.0.0.0
inet6 addr: ::1/128 Scope:Host
UP LOOPBACK RUNNINGMTU:16436Metric:1
RX packets:8274 errors:0 dropped:0 overruns:0 frame:0
TX packets:8274 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:8395613 (8.0 MiB)TX bytes:8395613 (8.0 MiB)
3.1.2 NetworkInterface類
可以使用NetworkInterface類提供的方法獲取本地計算機網絡接口相關的信息。盡管InetAddress類提獲取IP地址的方法,但是要想獲取本機的網絡接口的詳細信息,還需要依賴NetworkInterface接口中的方法。通過NetworkInterface接口,可以獲取本機配置的網絡接口的名字,IP列表(包括IPV4和IPV6),網卡地址,最大傳輸單元(MTU),接口狀態(開啟/關閉)、接口網絡類型(點對點網絡、回環網絡)等信息。Graphic3-3列出來NetworkInterface中可用的公有方法。從Graphic3-3可以看出,NetworkInterface沒有可見的構造方法,NetworkInterface內部也是使用靜態方法來構造NetworkInterface實例的(簡單工廠方法)。此外,每個NetworkInterface內部可以包含多個NetworkInterface對象,這就構成了一種樹結構(合成模式),而且每個NetworkInterface內部保持一個指向父NetworkInterface的引用。
Demo3-3中給出了一個使用NetworkInterface獲取本機eth0網絡接口IPV4地址的一個示例程序,首先通過NetworkInterface的getByName靜態方法,獲取一個關于eth0的NetworkInterface實例,之后調用NetworkInterface的getInetAddresses獲取配置在eth0上的所有IP地址(這時有可能獲取到多個IP,因為一個網絡接口可以配置多個IP),通過遍歷獲取的InetAddress,判斷如果是IPV4,則將這個IP地址輸出出來。需要提示的是,一般每臺計算機都會在別名為eth0的網絡接口上配置公網的IPV4或IPV6的地址,因此,直接使用eth0,即可獲取配置的IP地址信息,此外還有一個別名為lo的網絡接口,用來進行回環測試,其配置的IPV4一般為127.0.0.1。Demo3-3中給出的例子解決了InetAddress調用getLocalHost方法無法正確獲取本機IP地址的問題。為了保守起見(防止有的計算機沒有為網絡端口起名為eth0),demo3-4給出了一個更一般的方法。在Demo3-4中,先通過NetworkInterface的靜態方法getNetworkInterfaces獲取本機的所有網絡接口的父接口,之后遍歷這個父接口獲取下面的子接口,(在Configuration1和Configuration2中都配置了兩個子接口,一個名字為eth0,一個名字為lo),之后遍歷子接口的IP地址,輸出結果。并且在輸出中分辨出是IPV4的地址,還是IPV6的地址。
Graphic3-3 NetworkInterface類
Demo3-3 獲取本機IPV4的地址
package com.upc.upcgrid.guan.network.chapter03;
import java.net.InetAddress;
import java.net.NetworkInterface;
import java.net.SocketException;
import java.util.Enumeration;
public class NetworkInterfaceTest {
public static void main(String[] args) throws SocketException {
NetworkInterface ni = NetworkInterface.getByName("eth0");
Enumeration ias = ni.getInetAddresses();
for(;ias.hasMoreElements();)
{
InetAddress ia = ias.nextElement();
if(ia instanceof InetAddress)
System.out.println(ia);
}
}
}
Demo3-3的執行結構
在Configuration3-1下:
/202.194.158.128
在Configuration3-2下:
/202.194.158.184
Demo3-4 測試本機的IP地址
package com.upc.upcgrid.guan.network.chapter03;
import java.net.Inet4Address;
import java.net.Inet6Address;
import java.net.InetAddress;
import java.net.NetworkInterface;
import java.net.SocketException;
import java.util.Enumeration;
public class NetworkInterfaceTest2 {
public static void main(String[] args) throws SocketException {
Enumeration nis = NetworkInterface.getNetworkInterfaces();
for(;nis.hasMoreElements();)
{
NetworkInterface ni = nis.nextElement();
Enumeration ias = ni.getInetAddresses();
for(;ias.hasMoreElements();)
{
InetAddress ia = ias.nextElement();
if(ia instanceof Inet4Address && !ia.getHostAddress().equals("127.0.0.1"))
{
System.out.println("ip v4 : "+ia);
}else if(ia instanceof Inet6Address && !ia.equals(""))
{
System.out.println("ip v6 : "+ ia);
}
}
}
}
}
Demo3-4的執行結果:
Configuration3-1 下的執行結果:
ip v4 : /202.194.158.128
Configuration3-2下的執行結果:
ip v6 : /fe80:0:0:0:2e0:4cff:fe3d:c273%2
ip v6 : /2001:da8:7006:8003:2e0:4cff:fe3d:c273%2
ip v4 : /202.194.158.184
ip v6 : /0:0:0:0:0:0:0:1%1
3.1.3 簡單總結
InetAddress用于表示一個IP地址,其兩個子類Inet4Address和Inet6Address分別表示IPV4和IPV6兩種類型的地址。使用InetAddress的getByName方法可以獲取遠程服務的IP地址(通過DNS服務獲取的),使用getAllByName方法可以獲取遠程指定服務的所有服務主機的IP地址。使用getLocalHost方法可以獲取本地IP地址,但是這種方式并不可靠,當出現多張網卡,或一個網絡接口配置了多個IP,或者不同的操作系統類型,都不能保證能夠獲得想要的IP。
NetworkInterface可以獲取本機網絡接口的相關信息,包括硬件地址,MTU,所有的IP地址等信息,需要獲取本機IP時,最好使用NetworkInterface對配置的IP地址進行篩選。
創作挑戰賽新人創作獎勵來咯,堅持創作打卡瓜分現金大獎總結
以上是生活随笔為你收集整理的java什么是网络接口_java 网络编程 -- IP地址的表示与网络接口信息的获取(InetAddress和NetworkInterface)...的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: java list作为参数传递_Java
- 下一篇: java虚拟机编译_[四] java虚拟