1. socket 编程模型
socket编程分为服务端以及客户端,客户端以及服务端一般按照以下步骤进行编写。
服务端
1. 新建Socket服务端对象
2. 设置监听端口
3. 进行端口监听,阻塞式
4. 如果有客户端连接取得客户端,处理连接
客户端
1. 新建Socket客户端对象
2. 绑定监听端口( 和服务器一样)以及IP(服务器地址)
3. 处理客户端连接
2. 一个聊天服务端以及客户端的实现(多线程)
实现思想:主要就是按照以上的步骤进行编写,只不过吧处理socket的过程单独取出来,使用线程监听当前服务端的socket以及客户端的socket的输入输出流,并且这些流进行处理。
Bugs:BufferReader阻塞问题,主要原因是一开始BufferReader.readLines()读取不到数据从而导致阻塞,解决办法是使用inputStream的byte数组读取固定字节的数据。
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.Random;
//服务端实现
public class SocketService {
private ServerSocket serverSocket;
//接受连接产生的socket
private Socket socket;
public void init(int port,String name){
Random random = new Random();
try {
serverSocket = new ServerSocket(port);
System.out.println("服务器成功启动,端口为"+String.valueOf(port));
while(true){
socket = serverSocket.accept();
System.out.println("有客户端连接");
process(socket,name);
/*new Thread(new HandleProcess(socket,name+String.valueOf(random.nextInt()))).start();*///多线程处理器,选择开启
}
} catch (IOException e) {
e.printStackTrace();
}
}
public void process(Socket socket,String name){
new Thread(new SocketInputProcess(socket, name)).start();
new Thread(new SocketOutputProcess(socket)).start();
}
public static void main(String[] args) {
SocketService socketService = new SocketService();
socketService.init(9999,"客户端");
}
}
import java.io.IOException;
import java.net.Socket;
\\客户端实现
public class SocketClient {
private Socket socket = null;
public void init(int port,String name){
try {
socket = new Socket("0.0.0.0",port);
System.out.println("客户端启动成功");
process(socket,name);
} catch (IOException e) {
e.printStackTrace();
}
}
private void process(Socket socket,String name) {
new Thread(new SocketInputProcess(socket,name)).start();
new Thread(new SocketOutputProcess(socket)).start();
}
public static void main(String[] args) {
SocketClient socketClient = new SocketClient();
socketClient.init(9999,"服务器");
}
}
import java.io.*;
import java.net.Socket;
//处理socket输入流
public class SocketInputProcess implements Runnable {
private Socket socket;
private String name;
public SocketInputProcess(Socket socket,String name) {
this.socket = socket;
this.name = name;
}
public void run() {
while (true) {
try {
InputStream inputStream = socket.getInputStream();
byte[] buffer = new byte[1024];
int len = inputStream.read(buffer,0,1024);
if(len != -1) {
System.out.println(name+" : "+new String(buffer, 0, len));
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
import java.io.*;
import java.net.Socket;
//处理socket输出流
public class SocketOutputProcess implements Runnable{
private Socket socket;
public SocketOutputProcess(Socket socket) {
this.socket = socket;
}
public void run() {
while (true) {
//获取控制台输入流
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(System.in));
int t;
StringBuilder sendText = new StringBuilder();
try {
while ((char) (t = bufferedReader.read()) != '\n') {
sendText.append((char) t);
}
//获取socket输出流
BufferedWriter bufferedWriter = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream()));
bufferedWriter.write(sendText.toString());
bufferedWriter.flush();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
import java.net.Socket;
//多线程处理器,此代码可以在服务端注释地方取消,但是有些bug
public class HandleProcess implements Runnable{
private Socket socket;
private String name;
public HandleProcess(Socket socket, String name){
this.socket = socket;
this.name = name;
}
public void run() {
new Thread(new SocketInputProcess(socket, name)).start();
new Thread(new SocketOutputProcess(socket)).start();
}
}
网友评论