Java 使用Socket实现简易聊天室(新手控制台版)

一.服务器端思路整理

        想要实现聊天室,对于服务器端由于需要一直监听用户的连接以及用户的消息发送,所以需要多线程来为每一个用户分配一个线程来实现功能。

实现start方法,创建serverSocket链接,死循环用以监听客户端用户的链接,当一个用户链接之后,就为其新开一个线程。通过这个新开的线程来实现对每个用户的功能。

public void start() throws IOException {
		ServerSocket server = new ServerSocket(8888);
		while(true) {
			Socket socket = server.accept();
			System.out.println(socket.getInetAddress().getHostAddress()+"正在链接!!!");
			ThreadSocket client = new ThreadSocket(socket);
			new Thread(client).start();
		}
	}

创建一个成员变量用来储存每一个用户的线程:

List<ThreadSocket> clients = new ArrayList<ThreadSocket>();

 我是创建了一个线程内部类,方便我直接使用这个线程数组,因为在一个用户登录的时候,服务器会给每一个用户广播一条欢迎消息,每个用户连接只有一次,所以我选择在线程的构造函数中将此线程添加到线程数组,并执行广播方法send(),此方法通过遍历线程数组,给每个线程的socket添加输出流,推送欢迎消息

public class ThreadSocket implements Runnable{
		
		Socket socket;
		String name;
		public ThreadSocket(Socket socket) throws IOException {			
			this.socket = socket;
			BufferedReader br = new BufferedReader(new InputStreamReader(socket.getInputStream()));
		    name = br.readLine();
		    String welcome = name+"["+socket.getInetAddress().getHostAddress()+"]来到了房间";
		    clients.add(this);
		    send(welcome);
		    System.out.println(welcome);
		}


		private void send(String welcome) throws IOException {
			for (ThreadSocket c : clients) {
				BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(c.socket.getOutputStream()));
			    bw.write(welcome);
			    bw.newLine();
			    bw.flush();		
			}
		}
		
	}

单独讲此线程的run方法:由于用户发送消息需要服务器一直监听,等待接受,所以必须写在死循环中,需要同客户端约定一个退出方式,因为一旦一方关闭,另一方socket.getInputStream()就会接受不到,此时程序会不断循环输出异常。

public void run() {
			while(true) {
				BufferedReader br;
				try {
					br = new BufferedReader(new InputStreamReader(socket.getInputStream()));
					String msg = br.readLine();
					String name1 = name+"["+socket.getInetAddress().getHostAddress()+"]";
					if(msg.equals("byebye")) {
						System.out.println(name1+"离开了聊天室");
						send(name1+"离开了聊天室");
						clients.remove(this);
						socket.close();
						break;
					}
					send(name1+":"+msg);
				    System.out.println(name1+":"+msg);
				} catch (IOException e) {
					e.printStackTrace();
				}
			    
			}
		}

主方法:通过对象调用非静态方法

public static void main(String[] args) throws IOException {
		new Server().start();
	}

二.客户端

主要注意的就是客户端与服务器端的发送接受关系,必须一一对应好,同样,客户端单线程实现不了一直监听服务器推送信息以及一直监听用户发送信息,在规定的退出指令中,需要注意当客户端输入推出指令后,客户端等待服务器推送的消息的线程仍在等待,所以我让服务器给本人也推送一个退出信息,不然也会爆出异常。

public class Client {
	
	public static void main(String[] args) {
		Socket socket=null;
		try {
			socket = new Socket("10.7.184.72",8888);
			BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream()));
		    System.out.println("请输入用户名:");
		    Scanner sc = new Scanner(System.in);
			bw.write(sc.next());
		    bw.newLine();
		    bw.flush();
		    BufferedReader br = new BufferedReader(new InputStreamReader(socket.getInputStream()));
		    System.out.println(br.readLine());
			ClientThread clientThread = new ClientThread(socket);
			clientThread.start();
			while(true) {
			    System.out.print("请输入发送的内容:");
			    String input = sc.next();
				bw.write(input);
				bw.newLine();
			    bw.flush();	
			    if(input.equals("byebye")) {
					clientThread.interrupt();
			    	break;
			    }
			}
		} catch (IOException e) {
			// TODO 自动生成的 catch 块
			e.printStackTrace();
		}
		
	}
	
}

客户端新开线程类:当用户输入退出指令后,while循环判定为false,但是此时线程还在br = new BufferedReader(new InputStreamReader(socket.getInputStream()));等待消息,所以跟服务器的关系发送要对应好。

class ClientThread extends Thread{
	Socket socket;
	public ClientThread(Socket socket) {
		this.socket=socket;
	}
	
	@Override
	public void run() {
		while (!Thread.interrupted()) {
			BufferedReader br;
			try {
				br = new BufferedReader(new InputStreamReader(socket.getInputStream()));
			    System.out.println(br.readLine());
			} catch (IOException e) {
				// TODO 自动生成的 catch 块
				e.printStackTrace();
			}
		}
	}
}

三.运行截图:

服务器端:

客户端:

 

 

此为新手向简易聊天室,大家有什么问题和建议,欢迎提出,大家一起讨论。

 

  • 11
    点赞
  • 59
    收藏
    觉得还不错? 一键收藏
  • 6
    评论
Java中可以利用Socket实现一个简单的聊天。首先需要创建一个服务器端和多个客户端。服务器端负责接收客户端的连接请求,并负责转发客户端发送的消息给其他客户端。客户端则负责连接服务器,并发送和接收消息。 服务器端的实现需要创建一个ServerSocket来监听客户端的连接请求,在接收到客户端连接请求时,创建一个新的线程来处理每个客户端的消息。服务器端接收到客户端的消息后,需要遍历所有的客户端连接,并将消息发送给每个客户端。 客户端的实现需要创建一个Socket来连接服务器端,然后通过输入输出流来发送和接收消息。客户端需要不断地监听服务器端的消息,并将接收到的消息显示在界面上。同时客户端也需要不断地监测用户输入,并将用户输入的消息发送给服务器端。 在实现聊天时,需要考虑到多个客户端之间的通信以及消息的发送和接收。可以使用线程来处理不同客户端的消息,并使用集合来保存所有连接的客户端。同时还需要考虑到消息的格式和编码方式,确保消息的正确传输和显示。 总之,通过JavaSocket编程,可以实现一个简单的多客户端聊天。这需要对Socket编程有一定的了解,并且需要考虑到多线程、消息传输等问题。通过合理的设计和实现,可以让多个用户在同一个聊天实现实时的消息交流。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值