JAVA网络编程

网络可以实现资源共享和通信,使用java.net包可以实现java的网络功能。java.net包为网络提供了功能强大的基础

java.net包

套接字相关类

Web相关类

网络

实现资源共享和通信

连接终端系统(主机)的通信系统

网络适配器

计算机通过线缆连接

网络接口卡NIC用于将计算机连接至线缆,也称为网络适配器

网络中计算机之通信的规则

常用的协议
    1.超文本传输协议HTTP
    2.文件传输协议FTP
    3.简单邮件传输协议SMTP
    4.网络新闻传输协议NNTP

端口

用于实现程序间的通信

常用的端口

    Telnet协议 23

    简单邮件传输协议 25

    文本传输协议 21
    超文本传输协议 80

客户端/服务器模式

又称为智能服务器/智能客户端体系结构

服务器和客户端共同承担计算

1.客户端
    向另一台计算机请求服务的计算机

2.服务器

    处理客户端请求的计算机

优点:

    服务器和客户端分摊工作

    服务器可以同时为数前台客户端服务

    多个客户端可以同时访问服务器

IP与DNS

IP地址

连接至网络的每台计算机都是唯一的

32为数字,四个用点号分隔的数字

包括网络ID和主机ID

网络的类包括A、B、C和D类

域名系统

将特定IP地址映射至字符串

映射由域名服务器系统维护

Java.net包

可用的类

1.InetAddress

2.Socket、ServerSocket和SocketImpl

3.DatagramPacket和DatagramSocket

4.URL、URLConnection和URLEncoder

套接字

是Internet通信的端点

与主机地址和端口地址相关联

客户端与服务器通过套接字建立连接和进行通信

    1.TCP/IP套接字
        较可靠的双向流协议

        发送任意属性的数据

        提供消息确认、错误检测和错误恢复等服务

    2.UDP套接字
        比较不可靠

InetAddress

封装IP地址和DNS

工厂方法用于创建实例

1.InetAddress getLocalHost()

2.InetAddress getByName(String HostName)

package com.lizhenhua.test;

import java.net.InetAddress;
import java.net.UnknownHostException;

public class InetAddressTest {
public static void main(String[] args) {
try {
//获取本机ip地址
InetAddress address = InetAddress.getLocalHost();
System.out.println(“本机IP地址:” + address);

        //根据域名,通过DNS域名解析,获得相应服务的主机地址
        InetAddress add2 = InetAddress.getByName("www.163.com");
        System.out.println("网易服务器主机:" + add2);

        //根据字符串表现形式的IP地址获得相应的主机地址(若果网络上有该IP地址的话)
        InetAddress add3 = InetAddress.getByName("192.168.0.22");
        System.out.println("IP地址为192.168.0.22的主机:" + add3);

        //根据机器名获得相应的主机地址(如果网络上有该机器名的话)
        InetAddress add4 = InetAddress.getByName(add3.getHostName());
        System.out.println("机器名为的本地主机名:" + add4);

        //打印本机IP地址相关参数

        //返回IP地址字符串
        String HostAddress = address.getHostAddress();
        //获取本机的主机名。
        String hostName = address.getHostName();
        //返回本机的原始的IP地址
        byte[] IP = address.getAddress();


        //在给定主机名的情况下,根据系统上配置的名称服务返回其 IP 地址所组成的数组。
        InetAddress[] baidus = InetAddress.getAllByName("www.baidu.com");
        //在给定原始 IP 地址的情况下,返回 InetAddress 对象。
        //获得本机的IP地址对象
        InetAddress localhost = InetAddress.getByAddress(IP);

        for (InetAddress inetAddress : baidus) {
            System.out.println("IP地址:"+inetAddress.getHostAddress());
            System.out.println("IP地址对应的主机名:"+inetAddress.getHostName());
        }

    } catch (UnknownHostException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
}

}

本机IP地址:PCOS-10271310/192.168.1.102
网易服务器主机:www.163.com/222.186.132.123
IP地址为192.168.0.22的主机:/192.168.0.22
机器名为的本地主机名:/192.168.0.22
IP地址:14.215.177.38
IP地址对应的主机名:www.baidu.com
IP地址:14.215.177.37
IP地址对应的主机名:www.baidu.com

Socket

建立服务器和客户端之间的连接

构造函数

Socket(String hostName,int port)

Socket(InetAddress a ,int port)

可用方法

InetAddress getInetAddress()
int getPort()
int getLocalPort()

ServerSocket

accept( ) 方法用于等待客户端触发通信

构造函数

ServerSocket(int port)
ServerSocket(int port, int maxqu)

Socket编程

编写服务器端程序:

创建一个服务器套接字(ServerSocket),绑定到指定端口;
调用accept方法,侦听来自客户端的请求,如果客户发出请求,则接受连接,返回通信套接字(Socket);
调用Socket的getInputStream和getOutputStream方法,获得输入/输出流,开始网络数据的接收和发送;
关闭通信套接字,关闭服务器套接字。

编写客户端程序:
创建一个套接字(Socket) ,向服务器的侦听端口发出请求;
与服务器正确连接后,调用Socket的getInputStream和getOutputStream方法,获得输入/输出流,开始网络数据的接收和发送;
关闭通信套接字。

关于IO流

计算机系统将除了CPU和内存以外其它所有设备都当成文件来处理,包括网络终端(网卡)也不例外;
在两台主机之间通过socket建立握手连接之后,主要是通过输入/输出流来接收和发送数据,实际上,对于网络的操作,绝大部分是在操作IO流;
实际上操作网络端口流与操作磁盘文件流的原理是相似的;
出于效率的考虑,scoket使用的是字节流,但是在实际操作中,字节往往会带来不便,所以我们一般会把字节流改造成字符流后进行操作。

对于InputStream,先使用InputStreamReader转化成字符流;
然后再使用BufferedReader建立缓冲,以提高效率,
如:
InputStream is = socket.getInputStream();
InputStreamReader isr = new InputStreamReader(is);
BufferedReader in = new BufferedReader(isr);
数据报

通信的一种报文类型

两个类
    DatagramPacket
    数据容器
    DatagramSocket
    发送或接收DatagramPacket


DatagramSocket

用于发送或接收DatagramPacket

构造函数

DatagramSocket()
DatagramSocket(int port)

可用方法
void send(DatagramPacket d)
void receive(DatagramPacket p)
void close()

DatagramPacket
起到数据容器作用的类

构造函数
DatagramPacket(byte[] data,int size)
DatagramPacket(byte[] data,int size,InetAddress i,int port)

URL

指向Internet上的资源文件

URL类提供API来访问Internet上的信息

URL的组件
    协议
    IP地址或主机名
    端口号
    实际文件路径

URL

构造函数

URL(String urlname)
URL(String protocol, String hostname, int port, String path)
URL(String protocol, String hostname, String path)

URLConnection
抽象类
用于封装由URL表示的Web对象的链接
提供进一步了解远程资源的方法

可用方法
URLConnection openConnection*(
String getContentType()
long getLastModified()
int getContentLength()


URLEncoder
将文本字符串转换为可以用作URL的形式

提供方法
encode()
1.将空格转换为加号(+)
2.将%用作转义码,进行特殊字符的编码

总结

java.net包
套接字相关类
Web相关类

OSI:Open Systems InterConnection;开放式系统互连。它为分层模型,将整个网络分为七层,使得网络中的计算机可以相互的以标准化交换信息,用于不同设备但又相互联

1.物理层

检测物理方面的设置

2.数据链路层

控制网络层与物理层之间的通信

3.网络层

将网络地址翻译成对应的物理地址,并决定如何将数据从发送方路由到接收方

4.传输层

负责确保数据可靠、顺序、无错的传达到目的

5.会话层
负责在网络中的两节点建立和维持通信
6.表示层
象应用程序和网络之间的翻译官
7.应用层

负责对软件提供接口以使程序能使用网络服务

套接字(Socket)

套接字用于实现网络上客户端程序和服务器程序之间的连接。也就是说,网络上两个通信的程序之间总有一个连接,这个连接的端点称为套接字。套接字是在一个较低层次上进行通信的。

套接字负责网络上进程之间的通信,客户端程序可以向套接字里写入请求,然后服务器会处理这个请求,并把处理结果通过套接字送回。具体来说,服务器应用程序一般会侦听一个特定端口,用来等待客户的连接请求,当一个连接请求到达时,客户和服务器会建立一个通信连接,在连接过程中,客户被分配一个本地端口号并与一个Socket连接,客户通过写Socket来通知服务器,再通过读取Socket来获取服务器发送过来的信息。类似地,服务器也获取一个本地端口号,它需要一个新的端口号来侦听原始端口上的其他连接请求。服务器也给它的本地端口连接一个Socket,通过读写它来与客户通信。

Socket可以根据通信性质分类,这种性质对于用户是可见的。应用程序一般仅在同一类的套接字之间进行通信。不过只要底层的通信协议允许,不同类型的套接字之间也可以通信。

用户目前可以使用两种套接字,即流套接字和数据报套接字。流套接字提供了双向的、有序的、无重复的并且无记录边界的数据流服务。TCP是一种流套接字协议,数据报套接字支持双向的数据流,但并不保证是可靠、有序、无重复的,也就是说,一个以数据报套接字来接收信息的进程有可能发现信息重复了,或者和发出的顺序不同了。数据报套接字的一个重要特点是它保留了记录边界。UDP即是一种数据报套接字协议。

创建基于TCP协议的程序步骤:

1.服务器创建一个ServerSocket,然后调用accept()方法等待客户连接;
2.客户端创建一个Socket并请求与服务器建立连接。

3.服务器接受到请求连接,开始创建一个新的Socket与客户建立专线连接;

4.建立了连接的两个Socket在一个单独的线程(由服务器程序创建)上对话

5.服务器开始等待新的连接请求

Java实现数据报

在java中提供了两个类DatagramSocket和DatagramPacket支持数据报文方式通信

DatagramSocket:表示一个发送和接受数据报文的socket;发送的多个包可能经过不同的路径,并且可以任意顺序到达目的。

DatagramPacket:表示一个数据报文包。用来实现一个无连接包的传送服务。一条消息从一台机器发送到另一台机器的选径仅依赖这个包所包含的消息。

示例:

网络协议:TCP/IP协议

TCP协议:传输控制协议;用来对数据提供可靠的报文流传输和对上层应用的连接服务,TCP使用顺序的应答,能够按需重传报文用来在两个或多个主机之间建立面向链接的通信。

IP协议:用于管理管理客户端和服务器端之间的报文传送;它是所有internet协议的基石它是一个面向包的协议,是无连接的。

UDP协议

UDP协议:也称用户数据报协议;是IP协议的另一个主机到主机层协议。提供了一种基本的、低延时的称为数据报的传输

端口

端口是一个逻辑概念。每一个服务器都运行在该主机的一个对外开放的端口上。一个主机上可以有多种服务器,也就是有多个端口。程序员可以在创建自己的服务器程序时使用其它端口(即除了系统默认的端口)。端口常以数字编号,作为客户可指定一个端口号,用这个端口号来连接相应的服务器以接收服务。

Socket通信

一对一的Socket C/S通信

TCP是一种可靠的、基于连接的网络协议,在Internet上大都采用TCP/IP协议进行互联。网络上的两个进程采用C/S模式进行通信。当两台主机准备进行交谈时,都必须建立一个Socket,其中一方作为服务器打开一个Socket并侦听来自网络的连接请求,另一个作为客户,它向网络上的服务器发送请求,通过Socket与服务器传递信息,要建立连接,只需指定主机的IP地址和端口即可。

void close() 关闭此套接字。

InetAddress getInetAddress() 返回套接字连接的地址。

int getLocalPort() 返回此套接字绑定的本地端口。

SocketAddress getLocalSocketAddress() 返回此套接字绑定的端点的地址,如果尚未绑定则返回null。

int getSoTimeout() 重新恢复SO_TIMEOUT的设置。

boolean isClosed() 返回套接字的关闭状态。

void setSoTimeout(int timeout) 启用/禁用带有指定超时值的SO_TIMEOUT,以毫秒为单位。

String toString() 将套接字的实现地址和实现端口以String型返回。

InetAddress

InetAddress类主要是用来得到所指定的网络地址,InetAddress类没有直接显式的构造函数。要生成一个InetAddress对象,必须运用一个可用的工厂方法。工厂方法(factory method)仅是一个类中的静态方法返回一个该类实例的约定。这是在一个带有各种参数列表的重载构造函数中完成的,当持有惟一方法名时可使结果更清晰。

InetAddress有三个方法可以用来创建InetAddress的实例

static InetAddress getLocalHost( ) throws UnknownHostException

static InetAddress getByName(String hostName) throws UnknownHostException
static InetAddress[ ] getAllByName(String hostName)     throws UnknownHostException

InetAddress类的非静态方法

boolean equals(Object other)如果对象具有和other相同的Internet地址则返回true。

byte[ ] getAddress( ) 返回此InetAddress对象的原始 IP 地址。

String getHostAddress( ) 返回与InetAddress对象相关的主机地址的字符串。

String getHostName( )返回与InetAddress对象相关的主机名的字符串。
int hashCode( ) 返回调用对象的散列码。
boolean isMulticastAddress( ) 如果Internet地址是一个多播地址则返回true;否则返回false。
String toString( ) 返回主机名字符串和IP地址。

URL

URL类封装了使用统一资源定位器(Uniform Resource Locator)访问一个WWW上的资源的方法。这个类可以生成一个寻址或指向某个资源的对象。URL类生成的对象指向WWW资源(Web页、文本文件、图形文件、声频片段等等) 

URL的基本表示方法是:

Protocol://hostname:port/resourcename#anchor

构造方法

public URL (String spec)    通过一个表示URL地址的字符串可以构造一个URL对象。如以下语句:
URL urlBase=new URL("http://www. 263.net/");

public URL(URL context, String spec) 通过基URL和相对URL构造一个URL对象。如以下语句:
URL net263=new URL ("http://www.263.net/");
URL index263=new URL(net263, "index.html")


public URL(String protocol, String host, String file);

URL  url=new URL("http", "www.gamelan.com", "/pages/Gamelan.net. html");

public URL(String protocol, String host, int port, String file);

URL gamelan=new URL("http", "www.gamelan.com", 80,                  "Pages/Gamelan.network.html"); 

URL常用方法

public String getProtocol()     获取该URL的协议名。
public String getHost()     获取该URL的主机名。
public int getPort()        获取该URL的端口号,如果没有设置端口,返回-1。
public String getFile()     获取该URL的文件名。
public String getQuery()    获取该URL的查询信息。
public String getPath()     获取该URL的路径。
public String getAuthority()    获取该URL的权限信息。
public String getUserInfo()     获得使用者的信息。
public String getRef()      获得该URL的引用。 

URL类的应用 

URL类经常用于下载网络资源,URL通过构造函数(构造函数为URL地址)可以得到一个对象,该对象的openStream()方法可以得到InputStream对象,得到InputStream就可以把网站上的资源下载下来了,下面是一个实例,使用URL类下载某个网站上的一张图片并保存到本地。 

URL url=new URL(“http://images.sohu.com/uiue/sohu_logo/beijing2008/sohu.gif“);
InputStream in = url.openStream();
FileOutputStream fout=new FileOutputStream(new File(“sohu.gif”));
int a=0;
while(a>-1)
{
//读入数据
a=in.read();
//写出数据
fout.write(a);
}

    fout.close();
    in.close();

}

URL url=new URL(“http://www.baidu.com“);
BufferedReader in = new BufferedReader(new InputStreamReader(url.openStream()));
String line;
while((line=in.readLine())!=null){
System.out.println(line);
}
in.close( );
}catch(Exception e){
e.printStackTrace();
}

学习到这我们就可以在网络上搜索其他资源了,图片、声音、文件等等,所有的任何资源只要我们知道它的URL就可以用以上的方法“下载”到本地了,其实我们完全可以参照以上的思想做一个类似网络爬虫的软件或者是一个简单的下载器了,然后从网络上下载自己想要的资源。有兴趣的同学可以参考其他资料来尝试一下。

URLConnection

URL类中的openConnection()方法可生成一个URLConnection对象,URLConnection类的实例可用于读取和写入此URL引用的资源。在网络编程工作中,JAVA的URLConnection是一个常用的类,它提供了一个非常方便的接口,只要提供需要连接的主机的URL地址,使用URL类的openConnection()方法就可以得到一个HttpURLConnection的对象,其中HttpURLConnection类是URLConnection类的子类,然后在此基础上分析HTTP内容,完成相关任务。在这种方式下,使用者不必考虑底层的实现细节,避免了烦琐的Socket类的代码编写,因此比较常用。

URLConnection常用方法

String getHeaderField(String name) 返回指定的头字段的值。
InputStream getInputStream() 返回在此打开的连接读取的输入流。
String getContentEncoding() 返回content-encoding头字段的值。
int getContentLength() 返回content-length头字段的值。
String getContentType() 返回content-type头字段的值。
long getDate() 返回date头字段的值。

你可能感兴趣的:(java,网络,socket,网络编程)