JAVA基础之网络通信协议--TCP与UDP
个人理解:
了解区分UDP与TCP的不同,正常情况都是两者结合的使用模式!为了更好的传输,经常会开多线程进行传输的!
一、网络通信协议:
1、TCP/IP协议:
四层:应用层、传输层、网络层和链路层:
链路层:链路层是用于定义物理传输通道,通常是对某些网络连接设备的驱动协议,例如针对光纤、网线提供的驱动。
网络层:网络层是整个TCP/IP协议的核心,它主要用于将传输的数据进行分组,将分组数据发送到目标计算机或者网络。
传输层:主要使网络程序进行通信,在进行网络通信时,可以采用TCP协议,也可以采用UDP协议。
应用层:主要负责应用程序的协议,例如HTTP协议、FTP协议等。
2、IP地址和端口号:
①、IP地址,它可以唯一标识一台计算机:
以前为IPV4,现在是IPV6的16个字节表示地址。
②、端口号:两个字节:0-65535。一般为1024以上的端口号。
3、InetAddress类:
import java.net.InetAddress; import java.net.UnknownHostException; public class Demo01 { public static void main(String[] args) throws UnknownHostException { InetAddress inet=InetAddress.getByName("192.168.1.163");//里面是自己的ip地址 //从对象中获取IP地址 System.out.println(inet.getHostAddress()); //获取主机名 System.out.println(inet.getHostName()); //获取本地主机ip对象 InetAddress inet2=InetAddress.getLocalHost(); System.out.println(inet2.getHostAddress()); System.out.println(inet2.getHostName()); } }
二、UDP与TCP协议:
1、UDP协议:
User Datagram Protocol 用户数据报协议--无连接的通信协议:不能保证数据的完整性,随缘!!!64K以内。
2、TCP协议:
Transmission Control Protocol 传输控制协议---面向连接的通信协议:
在传输数据前先在发送端和接收端建立逻辑连接,然后再传输数据。
在TCP连接中必须要明确客户端与服务器端,由客户端向服务端发出连接请求,每次连接的创建都需要经过“三次握手”。第一次握手,客户端向服务器端发出连接请求,等待服务器确认,第二次握手,服务器端向客户端回送一个响应,通知客户端收到了连接请求,第三次握手,客户端再次向服务器端发送确认信息,确认连接。
三、UDP通讯:
1、DatagramPacket:数据打包类:
用于封装UDP通信中发送或者接收的数据。
2、DatagramSocket:“码头”:可以发送和接收DatagramPacket数据包
import java.io.IOException; import java.net.DatagramPacket; import java.net.DatagramSocket; import java.net.InetAddress; import java.net.SocketException; import java.net.UnknownHostException; //发送端 public class UDPSend { public static void main(String[] args) throws IOException { //封装数据 byte[ ] bytes="你好UDP".getBytes(); //封装ip地址 InetAddress inet=InetAddress.getByName("127.0.0.1"); //1。创建数据打包对象,封装要发送的数据、长度、接收端的IP地址和端口号 DatagramPacket dp=new DatagramPacket(bytes,bytes.length,inet,6000); //2.创建DatagreamSocket对象(快递公司) DatagramSocket ds=new DatagramSocket(); //3.发送数据包 ds.send(dp); //释放资源 ds.close(); } }
import java.io.IOException; import java.net.DatagramPacket; import java.net.DatagramSocket; import java.net.SocketException; //接收端 public class UDPReceive { public static void main(String[] args) throws IOException { //创建DatagramSocket对象,明确端口号 DatagramSocket ds=new DatagramSocket(6000); //2.创建字节数组负责接收发来的数据 byte [] bytes=new byte[1024]; //3.创建数据拆包对象 DatagramPacket dp=new DatagramPacket(bytes,bytes.length); //4.接收数据包 ds.receive(dp); //5.拆包 //获取接收的数据长度 int length=dp.getLength(); //获取发送端的IP地址 String ip=dp.getAddress().getHostAddress(); //获取发送端的端口号 int port =dp.getPort(); System.out.println("ip地址为:"+ip+"端口号为:"+port+"发送的内容为:"+new String(bytes,0,length)); } }
四、TCP通信:
1、ServerSocket类:服务器端;Socket类:客户端。
//服务器端 public class TCPServer { public static void main(String[] args) throws IOException { //1.创建服务器对象ServerSocket,明确端口号 ServerSocket server=new ServerSocket(8888); //2.调用accept方法,跟客户端创建连接,并获取连接的客户端对象 Socket socket=server.accept(); //3.明确目的地 File file=new File("D:\\nihao"); //如果该目录不存在则创建 if(!file.exists()){ file.mkdirs(); } String filename="oracle"+System.currentTimeMillis()+".txt"; //明确目的地 FileOutputStream fos=new FileOutputStream(file+File.separator+filename); //明确数据源 InputStream in=socket.getInputStream(); //开始复制 int len=0; byte[] bytes=new byte[1024]; while((len=in.read(bytes))!=-1){ fos.write(bytes,0,len); } //回复客户端 //获取字节输出流 ,回复客户端 OutputStream out =socket.getOutputStream(); out.write("上传成功".getBytes()); //释放资源 fos.close(); server.close(); } }
//客户端 public class TCPClient { public static void main(String[] args) throws UnknownHostException, IOException { //1.创建Socket对象,明确要连接的服务器地址和端口号 Socket socket =new Socket("127.0.0.1",8888); //2.明确数据源 FileInputStream fis=new FileInputStream("D:\\java\\a.txt"); //3.从socke对象中获取字节输出流,准备把读的文件字节写给服务器 OutputStream out=socket.getOutputStream(); //4.开始复制 int len=0; byte[] bytes=new byte[1024]; while((len=fis.read(bytes))!=-1){ out.write(bytes,0,len); } //结束输出流,告诉服务器结束了,不要读了 socket.shutdownOutput(); //接收服务器的回复 //1.从socket对象中获取字节输入流,接收服务器回复的数据 InputStream in=socket.getInputStream(); len=in.read(bytes); System.out.println(new String(bytes,0,len)); //释放资源 socket.close(); fis.close(); } }
2、多线程传输:
//线程任务对象 public class Upload implements Runnable { private Socket socket; public Upload() { }; public Upload(Socket socket) { this.socket = socket; }; public void run() { FileOutputStream fos = null; try { // 3.明确目的地 File file = new File("D:\\nihao"); // 如果该目录不存在则创建 if (!file.exists()) { file.mkdirs(); } String filename = "oracle" + System.currentTimeMillis() + ".txt"; // 明确目的地 fos = new FileOutputStream(file + File.separator + filename); // 明确数据源 InputStream in = socket.getInputStream(); // 开始复制 int len = 0; byte[] bytes = new byte[1024]; while ((len = in.read(bytes)) != -1) { fos.write(bytes, 0, len); } // 回复客户端 // 获取字节输出流 ,回复客户端 OutputStream out = socket.getOutputStream(); out.write("上传成功".getBytes()); } catch (IOException ex) { ex.printStackTrace(); } finally { // 释放资源 try { fos.close(); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } } } }
public class Demo { public static void main(String[] args) throws IOException { //1.创建服务器对象 ServerSocket server=new ServerSocket(8888); while(true){ //创建连接获取客户端对象 Socket socket=server.accept(); /*//创建线程(创建线程任务) new Thread(new Upload(socket)).start();*/ //创建线程任务 Upload up=new Upload(socket); //创建线程对象 Thread thread=new Thread(up); //开启线程 thread.start(); } } }