Java多线程处理多客户端的请求

什么是Socket和什么是Socket编程

Socket通常称为套接字,应用程序通常通过套接字向网络发出请求。Java语言中的Socket编程常用到Socket和ServerSocket这两个类,Socket用于端对端的通信,而ServerSocket用于服务端对象的创建,它们都位于Java.net包中

基于TCP的Socket编程

在这里插入图片描述

•从图可见,Socket 编程是由服务器端和客户端两部分组成的,并且二者是相互交错通信的,因此在编写代码时就不能像以前那样先把一个类写完毕之后再编写第二个类,而应该是交错式的同步编写。例如,先在服务端类中创建服务对象及 accept() 方法,然后编写客户端类,在客户端类中创建 Socket 对象,之后再切换到服务端类编写 OutputStream 对象。换句话说,在 Socket 编程中,服务端和客户端互为依赖,在编写代码时二者都需要借助对方的已有代码。

利用多线程处理多客户端请求

在这里插入图片描述

如图,客户端在请求连接客户端时,每个客户端会创建一个Socket,所以服务端在相应连接时,也会相应创建多个Socket,所以我们需要在相应连接时,每个客户端创建一个线程。明白思路后。

这里利用发生对象流,所以创建了一个student类

import java.io.Serializable;
//将要传递的对象序列化
public class Student implements Serializable {
    private int sid;
    private String name;
    private int age;
    public Student() {
    }
    public Student(int sid, String name, int age) {
        this.sid = sid;
        this.name = name;
        this.age = age;
    }
    public int getSid() {
        return sid;
    }
    public void setSid(int sid) {
        this.sid = sid;
    }
    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }
    @Override
    public String toString() {
        return "Student{" +
                "sid=" + sid +
                ", name='" + name + '\'' +
                ", age=" + age +
                '}';
    }
}

服务器线程代码

package NetWork.MuThread;

import NetWork.Base.Student;

import java.io.IOException;
import java.io.InputStream;
import java.io.ObjectInputStream;
import java.io.OutputStream;
import java.net.Socket;
import java.nio.charset.StandardCharsets;

public class ServerThread extends Thread{
    Socket socket;
    public ServerThread(Socket socket){
        this.socket=socket;
    }
    @Override
    public void run() {
        InputStream in=null;
        ObjectInputStream ois=null;
        Student student=null;
        OutputStream out=null;
        try {
             in = socket.getInputStream();
             ois =new ObjectInputStream(in);
             student = (Student)ois.readObject();
            System.out.println(student);
            socket.getInputStream();
             out =socket.getOutputStream();
            out.write("ok".getBytes(StandardCharsets.UTF_8));
            } catch (ClassNotFoundException e) {
                e.printStackTrace();
            } catch (IOException e) {
            e.printStackTrace();
        }finally {
            try {
               if(out !=null) out.close();
                if(ois !=null) ois.close();
                if(in !=null) in.close();
                if(socket !=null) socket.close();
            } catch (IOException e) {
                e.printStackTrace();
            }

        }
    }
}

服务端代码

import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;

public class ThreadMyServer {
    public static void main(String[] args) {
        ServerSocket serverSocket =null;

        try {
            serverSocket=new ServerSocket(8841);

            while (true){
//                每接收到一个客户机的申请连接,就创建一个线程
               Socket socket=serverSocket.accept();
                ServerThread serverThread =new ServerThread(socket);
                serverThread.start();
            }

        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

客户端代码一个示例

import java.io.*;
import java.net.Socket;

public class MyClient1 {
    public static void main(String[] args) {
        Socket socket =null;
        ObjectOutputStream oos=null;
        OutputStream out =null;
        BufferedReader reader=null;
        InputStream in=null;
        try {
             socket =new Socket("127.0.1",8841);
            Student student =new Student(1,"zs",23);
             out= socket.getOutputStream();
            oos = new ObjectOutputStream(out);
            oos.writeObject(student);
            socket.shutdownOutput();

             in = socket.getInputStream();
            reader= new BufferedReader(new InputStreamReader(in));
            String info;
            while ((info=reader.readLine())!=null){
                System.out.println("I am Cilent,接收到的消息"+info);
            }
        } catch (IOException e) {
            e.printStackTrace();
        }finally {
            try {
                if (reader != null) reader.close();
                if (in != null) in.close();
                if (oos != null) oos.close();
                if (out != null) out.close();
                if (socket != null) socket.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

能同时对多个客户端进行监听

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-7pcdoztm-1668592079582)(C:\Users\Administrator\AppData\Roaming\Typora\typora-user-images\image-20221116174731922.png)]

  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

柚子草莓吴彦祖

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值