1. TCP协议的通信特点
(1)面向连接的传输
(2)端到端的通信
(3)可靠性,确保传输数据的正确性,不出现丢失或乱序
(4)采用字节流方式,即以字节为单位传输字节序列
2.TCP编程模型
TCP一般用于C/S模式的应用程序,它们都会存在客户端和服务端两个部分。
服务端:
(1)创建一个服务端的Socket,指定一个端口号。(java.net.ServerSocket类)
ServerSocket ss=new ServerSocket(int 型的端口号);
(2)开始监听来自客户端的请求要求。
调用ServerSocket的accept()方法即可,即ss.accept();
(3)获得输出流或输入流。
Socket socket=ss.accept();
OutputStream os=socket.getOutputStream();//获得输出流
InputStream is=socket.getInputStream();//获得输入流
(4)调用输入流/输出流的read()和write()方法,进行数据的传输。如果是字符数据流,一般还可以用BufferedReader或PrintWriter进行数据的传输。
PrinterWriter pw=new PrintWriter(os);
pw.print(内容);
pw.flush();
或
InputStreamReader isr=new InputStreamReader(is);
BufferedReader br=new BufferedReader(isr);
(5)释放资源,关闭输出流/输入流、Socket和ServerSocket对象
pw.close();
socket.close();
ss.close();
客户端:
(1)创建Socket对象,建立与服务器端的连接。
Socket s=new Socket("IP地址",端口号);
(2)获得输出流或输入流
(3)调用输入流/输出流的read()和write()方法,进行数据的传输
(4)释放资源,关闭输出流/输入流、Socket对象
3.UDP协议的通信特点
(1)UDP是一个无连接协议,传输数据之前源端和终端不建立连接,当它想传送时就简单地去抓取来自应用程序的数据,并尽可能快地将它扔到网络上
(2)不需要维护连接状态,包括收发状态等
(3)字节开销很小
(4)吞吐量主要受应用软件生成数据的速率、传输带宽、源端和终端主机性能等因素的限制。
4.UDP编程模型
UDP一般用于安全性要求不高的点对点传输模式的应用程序,需要分为接收端和发送端两个部分。
(1)创建Socket,指定一个端口号。(java.net.DatagramSocket类)
DatagramSocket ds=new DatagramSocket(9999);
(2)对于接收消息的一端来说,提供一个byte数组进行数据的存储;而对于发送消息的一端,除此之外还需要提供对端的IP地址和端口号。
byte[] buff=new byte[1024]; //创建一个byte数字
DatagramPacket dp=new DatagramPacket(buff,1024); //创建一个数据包对象
或
String str="数据";
//用byte数组,创建数据包对象
DatagramPacket dp=new DatagramPacket(str.getByte(),0,str.length(),InetAddress.getByName("localhost"),9999);
(3)调用DatagramPacket的receive()或send()方法进行数据的接收或发送。
ds.receive(DatagramPacket对象);
或
ds.send(DatagramPacket对象);
(4)调用DatagramPacket的getData()方法得到byte数组的数据。
dp.getData();
(5)释放资源。
ds.close();
5.如何创建TCP通信的服务器端的多线程模型
(1)创建ServerSocket对象,指定监听的端口号。
(2)把accept()方法作为循环条件,循环监听客户端请求。
(3)创建线程类,定义一个Socket类型的成员变量,并定义一个可以为它赋值的构造方法。
(4)在run方法中使用socket变量进行任意的通信操作
(5)在主线程的循环体内开启一个线程,并传入accept()方法的返回值。
public class TCPServer{
public static void main(String[] args) throws Exception{
ServerSocket ss=new ServerSocket(8888);
Socket s=null;
while((s=ss.accept())!=null){
new MyThread(s).start();
}
ss.close();
}
}
//线程类
class MyThread extends Thread{
private Socket socket;
public MyThread(Socket socket){
super();
this.socket=socket;
}
//线程方法
public void run(){
try{
OutputStream os=socket.getOutputStream();
PrintWriter pw=new PrintWriter(os);
pw.print("now time ="+new Date());
pw.flush();
pw.close();
socket.close();
}catch(IOException e){
e.printStackTrace();
}
}
}