目录
一、Socket简介
二、实现基于TCP的Socket通信—服务端
三、实现基于TCP的Socket通信—客户端
四、服务器响应客户端
五、使用多线程实现多客户端的通信
一、Socket简介
1、Tcp协议是面向连接、可靠的、有序的、以字节流的方式发送数据
2、基于TCP协议实现网络通信的类
- 客户端的Socket类
- 服务器端的serverSocket类
3、Socket通信模型
4、实现TCP编程步骤
- 1、创建ServerSocket和Socket
- 2、打开连接到Socket的输入/输出流
- 3、按照协议对Socket进行读/写操作
- 4、关闭输入流、关闭Socket
二、实现基于TCP的Socket通信—服务端
ServerSocket介绍
ServerSocket 构造方法
ServerSocket重要方法
代码块
/**
* 实现基于TCP协议的Socket通信, 实现登录 服务端
*/
public class Service {
public static void main(String[] args) {
try {
//1.创建一个服务器Socket, 即ServerSocket,指定绑定端口, 并监听此端口
ServerSocket serverSocket = new ServerSocket(8888);
//2.调用accept()方法开始监听,等待客户端链接
System.out.println("------------服务器即将启动,等待客户端的连接");
Socket socket = serverSocket.accept();
//3.获取输入流 用来读取客户端发送的登录信息
InputStream is = socket.getInputStream();
//将字节流转换为字符流
InputStreamReader isr = new InputStreamReader(is);
//为输入流添加缓冲
BufferedReader br = new BufferedReader(isr);
String info = null;
//循环读取客户端数据
while ((info = br.readLine()) != null) {
System.out.println(" 我是服务器, 客户端说:" + info);
}
socket.shutdownInput(); //关闭输入流
//4.关闭资源
br.close();
isr.close();
is.close();
socket.close();
serverSocket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
三、实现基于TCP的Socket通信—客户端
Socket介绍
构造方法
主要方法
代码块
/**
* 实现基于TCP协议的Socket通信, 实现登录
* 客户端
*/
public class Client {
public static void main(String[] args) {
try {
//1、创建Socket,知名需要连接的服务器的地址和端口号
Socket socket = new Socket("localhost", 8888);
//2、连接创建后, 通过输出流向服务器端发送请求信息
OutputStream os = socket.getOutputStream();
//将输出流包装成打印流
PrintWriter pw = new PrintWriter(os);
pw.write("用户名:admin;密码:123");
pw.flush();
socket.shutdownOutput();//关闭输出流
//4、关闭相关资源
pw.close();
os.close();
socket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
运行结果:
四、服务器响应客户端
// 服务端
完整代码:
/**
* 实现基于TCP协议的Socket通信, 实现登录 服务端
*/
public class Service {
public static void main(String[] args) {
try {
//1.创建一个服务器Socket, 即ServerSocket,指定绑定端口, 并监听此端口
ServerSocket serverSocket = new ServerSocket(8888);
//2.调用accept()方法开始监听,等待客户端链接
System.out.println("------------服务器即将启动,等待客户端的连接");
Socket socket = serverSocket.accept();
//3.获取输入流 用来读取客户端发送的登录信息
InputStream is = socket.getInputStream();
//将字节流转换为字符流
InputStreamReader isr = new InputStreamReader(is);
//为输入流添加缓冲
BufferedReader br = new BufferedReader(isr);
String info = null;
//循环读取客户端数据
while ((info = br.readLine()) != null) {
System.out.println(" 我是服务器, 客户端说:" + info);
}
socket.shutdownInput(); //关闭输入流
//4、获取输出流,响应客户端的请求
OutputStream os = socket.getOutputStream();
PrintWriter pw = new PrintWriter(os);
pw.write("欢迎登录");
pw.flush(); //将缓存输出
//5.关闭资源
pw.close();
os.close();
br.close();
isr.close();
is.close();
socket.close();
serverSocket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
//客户端
完整代码
/**
* 实现基于TCP协议的Socket通信, 实现登录
* 客户端
*/
public class Client {
public static void main(String[] args) {
try {
//1、创建Socket,知名需要连接的服务器的地址和端口号
Socket socket = new Socket("localhost", 8888);
//2、连接创建后, 通过输出流向服务器端发送请求信息
OutputStream os = socket.getOutputStream();
//将输出流包装成打印流
PrintWriter pw = new PrintWriter(os);
pw.write("用户名:admin;密码:123");
pw.flush();
socket.shutdownOutput();//关闭输出流
//获取输入流,用来读取服务端的响应信息
InputStream is = socket.getInputStream();
BufferedReader br = new BufferedReader(new InputStreamReader(is));
String info = null;
while ((info = br.readLine()) != null){
System.out.println("我是客户端,服务器回应:"+ info);
}
//4、关闭相关资源
br.close();
is.close();
pw.close();
os.close();
socket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
五、使用多线程实现多客户端的通信
实现服务器与多个客户端进行通信, 可以接受多个客户端的请求并进行回复
应用多线程来实现服务器与多客户端之间的通信
1、服务器端创建ServerSocket,循环调用accept()等待客户端连接
2、客户端创建一个Socket并请求和服务器端连接
3、服务器端接受客户端请求,创建socket与该客户建立专线连接
4、建立连接的两个socket在一个单独的线程上对话
5、服务器端继续等待新的连接
代码块
import java.io.*;
import java.net.Socket;
/**
* 服务器端线程处理类
*/
public class ServerThread extends Thread {
//和本线程相关的类
Socket socket = null;
public ServerThread(Socket socket) {
this.socket = socket;
}
public void run() {
//3.获取输入流 用来读取客户端发送的登录信息
InputStream is = null;
PrintWriter pw = null;
OutputStream os = null;
BufferedReader br = null;
InputStreamReader isr = null;
try {
is = socket.getInputStream();
//将字节流转换为字符流
isr = new InputStreamReader(is);
//为输入流添加缓冲
br = new BufferedReader(isr);
String info = null;
//循环读取客户端数据
while ((info = br.readLine()) != null) {
System.out.println(" 我是服务器, 客户端说:" + info);
}
socket.shutdownInput(); //关闭输入流
//4、获取输出流,响应客户端的请求
os = socket.getOutputStream();
pw = new PrintWriter(os);
pw.write("欢迎登录");
pw.flush(); //将缓存输出
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
//5.关闭资源
if (pw != null)
pw.close();
if (os != null)
os.close();
if (br != null)
br.close();
if (isr != null)
isr.close();
if (is != null)
is.close();
if (socket != null)
socket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
Server类
/**
* 实现基于TCP协议的Socket通信, 实现登录 服务端
*/
public class Service {
public static void main(String[] args) {
try {
//1.创建一个服务器Socket, 即ServerSocket,指定绑定端口, 并监听此端口
ServerSocket serverSocket = new ServerSocket(8888);
Socket socket = null;
int count = 0;
//2.调用accept()方法开始监听,等待客户端链接
System.out.println("------------服务器即将启动,等待客户端的连接");
while (true){
socket = serverSocket.accept();
ServerThread thread = new ServerThread(socket);
thread.start();
count ++;
System.out.println("客户端的数量"+ count);
InetAddress inetAddress = socket.getInetAddress();
System.out.println("d当前客户端的IP"+ inetAddress.getHostAddress());
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
Client类
import java.io.*;
import java.net.Socket;
/**
* 实现基于TCP协议的Socket通信, 实现登录
* 客户端
*/
public class Client {
public static void main(String[] args) {
try {
//1、创建Socket,知名需要连接的服务器的地址和端口号
Socket socket = new Socket("localhost", 8888);
//2、连接创建后, 通过输出流向服务器端发送请求信息
OutputStream os = socket.getOutputStream();
//将输出流包装成打印流
PrintWriter pw = new PrintWriter(os);
pw.write("用户名:tom;密码:123");
pw.flush();
socket.shutdownOutput();//关闭输出流
//获取输入流,用来读取服务端的响应信息
InputStream is = socket.getInputStream();
BufferedReader br = new BufferedReader(new InputStreamReader(is));
String info = null;
while ((info = br.readLine()) != null){
System.out.println("我是客户端,服务器回应:"+ info);
}
//4、关闭相关资源
br.close();
is.close();
pw.close();
os.close();
socket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}