目录
网络通信
网络通信三要素(IP地址,端口号,协议
IP地址
InetAddress
端口号
协议
传输层的两个通信协议
UDP通信
java.net.Datagramsocket类
客户端
服务端
UDP通信多收多发
客户端
服务端
TCP通信
java.net.Socket类
客户端
服务端
TCP通信多收多发
客户端
服务端
群聊
网络通信
网络编程:可以让设备中的程序与网络上其他设备中的程序进行数据交互(实现网络通信的)
基本的通信架构有2种形式:CS架构(Client客户端/Server服务端)、BS架构(Browser浏览器/Server服务端)。
网络通信三要素(IP地址,端口号,协议
IP地址
IP(Internet Protocol):全称”互联网协议地址”,是分配给上网设备的唯一标志。
IP地址有两种形式:IPV4、IPV6
公网IP:是可以连接互联网的IP地址;
内网IP:也叫局域网IP,只能组织机构内部使用。
192.168.开头的就是常见的局域网地址,范围即为192.168.0.0--192.168.255.255,专门为组织机构内部使用
特殊IP地址
127.0.0.1、localhost:代表本机IP,只会寻找当前所在的主机。
IP常用命令
ipconfig:查看本机IP地址。
pingIP地址:检查网络是否连通
InetAddress
端口号
端口:标记正在计算机设备上运行的应用程序的,被规定为一个16 位的二进制,范围是0~65535。
分类
周知端口:0~1023,被预先定义的知名应用占用(如:HTTP占用 80,FTP占用21)
注册端口:1024~49151,分配给用户进程或某些应用程序。
动态端口:49152到65535,之所以称为动态端口,是因为它一般不固定分配某种进程,而是动态分配。
注意:我们自己开发的程序一般选择使用注册端口,且一个设备中不能出现两个程序的端口号一样,否则出错。
协议
通信协议:网络上通信的设备,事先规定的连接规则,以及传输数据的规则被称为网络通信协议
传输层的两个通信协议
UDP(User Datagram Protocol):用户数据报协议;
TCP(Transmission ControlProtocol):传输控制协议。
UDP协议
特点:无连接、不可靠通信;通信效率高
不事先建立连接,数据按照包发,一包数据包含:自己的IP、程序端口,目的地IP、程序端口和数据(限制在64KB内)等。
发送方不管对方是否在线,数据在中间丢失也不管,如果接收方收到数据也不返回确认,故是不可靠的。
TCP协议
特点:面向连接、可靠通信;通信效率相对不高哦
TCP的最终目的:要保证在不可靠的信道上实现可靠的传输,
TCP主要有三个步骤实现可靠传输:三次握手建立连接,传输数据进行确认,四次挥手断开连接
三次握手建立可靠连接
可靠连接:确定通信双方,收发消息都是正常无问题的!(全双工
传输数据会进行确认,以保证数据传输的可靠性
四次握手断开连接 确保双方数据的收发都已经完成
UDP通信
不事先建立连接:发送端每次把要发送的数据(限制在64KB内)、接收端IP、等信息封装成一个数据包,发出去就不管了
java.net.Datagramsocket类
客户端
服务端
可以获取是从哪发来的
记得最后加socket.close(); // 其实一般都不加,服务端永远不死
UDP通信多收多发
客户端
服务端
与多客户端连接,只需要客户端别指定端口号,让它默认分配,然后再启动一个客户端就行
TCP通信
通信双方事先会采用“三次握手”方式建立可靠连接,实现端到端的通信;底层能保证数据成功传给服务端。
java.net.Socket类
客户端
服务端
TCP通信多收多发
客户端
服务端
与多客户端同时通信——多线程
群聊
Client
package cn.ptz;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.net.Socket;
import java.util.Scanner;
public class Client {
public static void main(String[] args) throws Exception {
// 创建对象,请求与服务器连接
Socket socket = new Socket("127.0.0.1",7777);
new ClientReaderThread(socket).start();
// 从socket管道得到字节输出流
OutputStream os = socket.getOutputStream();
// 低级输出流包装成数据输出流
DataOutputStream dos = new DataOutputStream(os);
Scanner sc = new Scanner(System.in);
while (true){
System.out.println("请输入");
String msg = sc.nextLine();
if ("exit".equals(msg)){
System.out.println("退出");
dos.close();
socket.close();
break;
}
dos.writeUTF(msg);
dos.flush();
}
}
}
ClientReaderThread
package cn.ptz;
import java.io.DataInputStream;
import java.io.InputStream;
import java.net.Socket;
public class ClientReaderThread extends Thread{
private Socket socket;
public ClientReaderThread(Socket socket){
this.socket = socket;
}
@Override
public void run() {
try {
InputStream is = socket.getInputStream();
DataInputStream dis = new DataInputStream(is);
while (true){
try {
String msg = dis.readUTF();
System.out.println(msg);
}catch (Exception e){
System.out.println("客户退出" + socket.getRemoteSocketAddress());
Server.onlineSockets.remove(socket);
dis.close();
socket.close();
break;
}
}
}catch (Exception e) {
e.printStackTrace();
}
}
}
Server
package cn.ptz;
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.ArrayList;
import java.util.List;
public class Server {
public static List<Socket> onlineSockets = new ArrayList<>();
public static void main(String[] args) throws Exception {
System.out.println("服务器启动");
ServerSocket serverSocket = new ServerSocket(7777);
while (true){
Socket socket = serverSocket.accept();
onlineSockets.add(socket);
System.out.println("客户端连接" + socket.getRemoteSocketAddress());
new ServerReaderThread(socket).start();
}
}
}
ServerReaderThread
package cn.ptz;
import java.io.*;
import java.net.Socket;
public class ServerReaderThread extends Thread{
private Socket socket;
public ServerReaderThread(Socket socket){
this.socket = socket;
}
@Override
public void run() {
try {
InputStream is = socket.getInputStream();
DataInputStream dis = new DataInputStream(is);
while (true){
try {
String msg = dis.readUTF();
System.out.println(msg);
sendMsgToAll(msg);
}catch (Exception e){
System.out.println("客户退出" + socket.getRemoteSocketAddress());
Server.onlineSockets.remove(socket);
dis.close();
socket.close();
break;
}
}
}catch (Exception e) {
e.printStackTrace();
}
}
private void sendMsgToAll(String msg) throws IOException {
for (Socket onlineSocket : Server.onlineSockets) {
OutputStream os = onlineSocket.getOutputStream();
DataOutputStream dos = new DataOutputStream(os);
dos.writeUTF(msg);
dos.flush();
}
}
}