欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Java?Socket實現(xiàn)聊天室功能

 更新時間:2022年09月02日 16:24:43   作者:dreaming9420  
這篇文章主要為大家詳細介紹了Java?Socket實現(xiàn)聊天室功能,文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下

本文實例為大家分享了Java Socket實現(xiàn)聊天室的具體代碼,供大家參考,具體內(nèi)容如下

1 創(chuàng)建登錄判斷類UserLogin

import java.util.HashSet;
import java.util.Set;

public class UserLogin {

? ? public static boolean login(String username) {
? ? ? ? Set<String> set = initUser();
? ? ? ? // set中含有該username則登錄成功
? ? ? ? return set.contains(username);
? ? }

? ? public static Set<String> initUser() {
? ? ? ? Set<String> set = new HashSet<>();
? ? ? ? set.add("111");
? ? ? ? set.add("222");
? ? ? ? set.add("333");
? ? ? ? set.add("444");
? ? ? ? set.add("555");
? ? ? ? return set;
? ? }
}

2 創(chuàng)建登錄服務(wù)器LoginServer

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

public class LoginServer {
? ? public static void main(String[] args) {
? ? ? ? int port = 6666;
? ? ? ? try (ServerSocket serverSocket = new ServerSocket(port)) {
? ? ? ? ? ? System.out.println("登錄服務(wù)器已經(jīng)啟動");
? ? ? ? ? ? while (true) {
? ? ? ? ? ? ? ? Socket socket = serverSocket.accept();
? ? ? ? ? ? ? ? // 接收Client輸出的信息(username)
? ? ? ? ? ? ? ? InputStream inputStream = socket.getInputStream();
? ? ? ? ? ? ? ? BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
? ? ? ? ? ? ? ? String username = bufferedReader.readLine();
? ? ? ? ? ? ? ? // 調(diào)用登錄方法,判斷是否成功登錄
? ? ? ? ? ? ? ? OutputStream outputStream = socket.getOutputStream();
? ? ? ? ? ? ? ? PrintStream printStream = new PrintStream(outputStream);
? ? ? ? ? ? ? ? if (UserLogin.login(username)) {
? ? ? ? ? ? ? ? ? ? System.out.println(username + "登錄成功");
? ? ? ? ? ? ? ? ? ? // 登錄成功輸出"true"到Client
? ? ? ? ? ? ? ? ? ? printStream.println("true");
? ? ? ? ? ? ? ? } else {
? ? ? ? ? ? ? ? ? ? System.out.println(username + "登錄失敗");
? ? ? ? ? ? ? ? ? ? // 登錄失敗則輸出"false"到Client
? ? ? ? ? ? ? ? ? ? printStream.println("false");
? ? ? ? ? ? ? ? }
? ? ? ? ? ? ? ? printStream.flush();
? ? ? ? ? ? }
? ? ? ? } catch (IOException e) {
? ? ? ? ? ? e.printStackTrace();
? ? ? ? }
? ? }
}

3 創(chuàng)建聊天服務(wù)器ChatServer

import com.socket.socketChatroom.bio.thread.ChatThread;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.HashMap;
import java.util.Map;

public class ChatServer {
? ? // 保存當前聊天中的所有Map<username,Socket>
? ? public static Map<String, Socket> socketMap = new HashMap<>();

? ? public static void main(String[] args) {
? ? ? ? int port = 9999;
? ? ? ? try (ServerSocket serverSocket = new ServerSocket(port)) {
? ? ? ? ? ? System.out.println("聊天服務(wù)器已經(jīng)啟動");
? ? ? ? ? ? while (true) {
? ? ? ? ? ? ? ? Socket socket = serverSocket.accept();
? ? ? ? ? ? ? ? // 接收Client輸出的username
? ? ? ? ? ? ? ? InputStream inputStream = socket.getInputStream();
? ? ? ? ? ? ? ? BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
? ? ? ? ? ? ? ? String username = bufferedReader.readLine();
? ? ? ? ? ? ? ? System.out.println(username + "連接到聊天服務(wù)器");
? ? ? ? ? ? ? ? // 連接聊天服務(wù)器成功則將它的<username,Socket>放入socketMap中
? ? ? ? ? ? ? ? socketMap.put(username, socket);
? ? ? ? ? ? ? ? System.out.println(socketMap);
? ? ? ? ? ? ? ? // 因為可能有多個Client與ChatServer進行交互,所以一旦有Client連接成功就新創(chuàng)建一個線程與之交互
? ? ? ? ? ? ? ? new ChatThread(username,socket).start();
? ? ? ? ? ? }

? ? ? ? } catch (IOException e) {
? ? ? ? ? ? throw new RuntimeException(e);
? ? ? ? }
? ? }
}

4 創(chuàng)建客戶端Client

import com.socket.socketChatroom.bio.thread.ReadThread;
import com.socket.socketChatroom.bio.thread.WriteThread;

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

public class Client {
? ? public static void main(String[] args) {
? ? ? ? // 服務(wù)端地址,端口號
? ? ? ? String ip = "127.0.0.1";// 本機IP地址
? ? ? ? int port = 6666; // 必須和LoginServer的端口一樣
? ? ? ? try {
? ? ? ? ? ? Socket client = new Socket(ip, port);
? ? ? ? ? ? Scanner scanner = new Scanner(System.in);
? ? ? ? ? ? System.out.println("請輸入用戶名");
? ? ? ? ? ? String username = scanner.nextLine();
? ? ? ? ? ? // 將用戶名輸出到LoginServer
? ? ? ? ? ? OutputStream outputStream = client.getOutputStream();
? ? ? ? ? ? PrintStream printStream = new PrintStream(outputStream);
? ? ? ? ? ? printStream.println(username);
? ? ? ? ? ? printStream.flush();
? ? ? ? ? ? // 接收LoginServer輸出的是否登錄成功標志("true"或"false")
? ? ? ? ? ? InputStream inputStream = client.getInputStream();
? ? ? ? ? ? BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
? ? ? ? ? ? String state = bufferedReader.readLine();
? ? ? ? ? ? // 如果為"true",則為登錄成功,可以開始聊天
? ? ? ? ? ? if (Boolean.parseBoolean(state)) {
? ? ? ? ? ? ? ? chat(username);
? ? ? ? ? ? }
? ? ? ? } catch (IOException e) {
? ? ? ? ? ? e.printStackTrace();
? ? ? ? }
? ? }

? ? public static void chat(String username) {
? ? ? ? try {
? ? ? ? ? ? String ip = "127.0.0.1";// 本機IP地址
? ? ? ? ? ? int port = 9999;// 必須和ChatServer的端口一樣
? ? ? ? ? ? // 連接聊天服務(wù)器ChatServer
? ? ? ? ? ? Socket socket = new Socket(ip, port);
? ? ? ? ? ? // 將username輸出到ChatServer
? ? ? ? ? ? OutputStream outputStream = socket.getOutputStream();
? ? ? ? ? ? PrintStream printStream = new PrintStream(outputStream);
? ? ? ? ? ? printStream.println(username);
? ? ? ? ? ? printStream.flush();
? ? ? ? ? ? // 因為聊天的收發(fā)消息不一定是與同一個人,所以創(chuàng)建兩個線程分別用于收和發(fā)
? ? ? ? ? ? new ReadThread(socket).start();
? ? ? ? ? ? new WriteThread(socket).start();
? ? ? ? } catch (IOException e) {
? ? ? ? ? ? throw new RuntimeException(e);
? ? ? ? }
? ? }
}

5 創(chuàng)建服務(wù)器用于處理聊天的線程類ChatThread

import com.socket.socketChatroom.bio.server.ChatServer;

import java.io.*;
import java.net.Socket;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;

public class ChatThread extends Thread {
? ? private final String username;
? ? private final Socket socket;

? ? public ChatThread(String username, Socket socket) {
? ? ? ? this.username = username;
? ? ? ? this.socket = socket;
? ? }

? ? @Override
? ? public void run() {
? ? ? ? while (true) {
? ? ? ? ? ? try {
? ? ? ? ? ? ? ? // 接收Client的WriteThread線程輸出的消息
? ? ? ? ? ? ? ? InputStream inputStream = socket.getInputStream();
? ? ? ? ? ? ? ? BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
? ? ? ? ? ? ? ? String message = bufferedReader.readLine();
? ? ? ? ? ? ? ? System.out.println(username + "說: " + message);
? ? ? ? ? ? ? ? // 將當前所有在線的Client的username存入usernameSet中
? ? ? ? ? ? ? ? Map<String, Socket> socketMap = ChatServer.socketMap;
? ? ? ? ? ? ? ? Set<String> usernameSet = new HashSet<>();
? ? ? ? ? ? ? ? for (Map.Entry<String, Socket> map : socketMap.entrySet()) {
? ? ? ? ? ? ? ? ? ? usernameSet.add(map.getKey());
? ? ? ? ? ? ? ? }
? ? ? ? ? ? ? ? // 以"-"作為標識符,判斷是群聊還是單聊
? ? ? ? ? ? ? ? String[] values = message.split("-");
? ? ? ? ? ? ? ? if (values.length == 2 && usernameSet.contains(values[0])) { //單聊
? ? ? ? ? ? ? ? ? ? // values[0]為要指定發(fā)送的Client的username
? ? ? ? ? ? ? ? ? ? OutputStream outputStream = socketMap.get(values[0]).getOutputStream();
? ? ? ? ? ? ? ? ? ? PrintStream printStream = new PrintStream(outputStream);
? ? ? ? ? ? ? ? ? ? // values[1]為消息內(nèi)容
? ? ? ? ? ? ? ? ? ? printStream.println(username + "說: " + values[1]);
? ? ? ? ? ? ? ? ? ? printStream.flush();
? ? ? ? ? ? ? ? } else {//群聊
? ? ? ? ? ? ? ? ? ? // 將消息發(fā)送到除自己之外的所有Client
? ? ? ? ? ? ? ? ? ? for (String username : usernameSet) {
? ? ? ? ? ? ? ? ? ? ? ? if (socket != socketMap.get(username)) {
? ? ? ? ? ? ? ? ? ? ? ? ? ? OutputStream outputStream = socketMap.get(username).getOutputStream();
? ? ? ? ? ? ? ? ? ? ? ? ? ? PrintStream printStream = new PrintStream(outputStream);
? ? ? ? ? ? ? ? ? ? ? ? ? ? printStream.println(this.username + "說: " + message);
? ? ? ? ? ? ? ? ? ? ? ? ? ? printStream.flush();
? ? ? ? ? ? ? ? ? ? ? ? }
? ? ? ? ? ? ? ? ? ? }
? ? ? ? ? ? ? ? }
? ? ? ? ? ? } catch (IOException e) {
? ? ? ? ? ? ? ? throw new RuntimeException(e);
? ? ? ? ? ? }
? ? ? ? }
? ? }
}

6 創(chuàng)建客戶端Client用于發(fā)送消息的線程類WriteThread

import java.io.IOException;
import java.io.OutputStream;
import java.io.PrintStream;
import java.net.Socket;
import java.util.Scanner;

public class WriteThread extends Thread {
? ? private final Socket socket;

? ? public WriteThread(Socket socket) {
? ? ? ? this.socket = socket;
? ? }

? ? @Override
? ? public void run() {
? ? ? ? while (true) {
? ? ? ? ? ? try {
? ? ? ? ? ? ? ? // 獲取輸出流
? ? ? ? ? ? ? ? OutputStream outputStream = socket.getOutputStream();
? ? ? ? ? ? ? ? PrintStream printStream = new PrintStream(outputStream);
? ? ? ? ? ? ? ? // 鍵盤輸入要發(fā)送的消息,若為單聊,則以要發(fā)送的Client的username+"-",開頭,比如"111-hello",表示向111這個Client發(fā)送"hello"
? ? ? ? ? ? ? ? Scanner scanner = new Scanner(System.in);
? ? ? ? ? ? ? ? System.out.println("請輸入聊天內(nèi)容: ");
? ? ? ? ? ? ? ? String message = scanner.nextLine();
? ? ? ? ? ? ? ? // 輸出消息到ChatServer
? ? ? ? ? ? ? ? printStream.println(message);
? ? ? ? ? ? ? ? printStream.flush();
? ? ? ? ? ? } catch (IOException e) {
? ? ? ? ? ? ? ? throw new RuntimeException(e);
? ? ? ? ? ? }
? ? ? ? }
? ? }
}

7 創(chuàng)建客戶端Client用于接收消息的線程類ReadThread

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.Socket;

public class ReadThread extends Thread {
? ? private final Socket socket;

? ? public ReadThread(Socket socket) {
? ? ? ? this.socket = socket;
? ? }

? ? @Override
? ? public void run() {
? ? ? ? while (true) {
? ? ? ? ? ? try {
? ? ? ? ? ? ? ? // 從ChatServer獲取消息
? ? ? ? ? ? ? ? InputStream inputStream = socket.getInputStream();
? ? ? ? ? ? ? ? BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
? ? ? ? ? ? ? ? String message = bufferedReader.readLine();
? ? ? ? ? ? ? ? System.out.println(message);
? ? ? ? ? ? } catch (IOException e) {
? ? ? ? ? ? ? ? throw new RuntimeException(e);
? ? ? ? ? ? }
? ? ? ? }
? ? }
}

項目結(jié)構(gòu)如下圖

8 測試

先運行LoginServer和ChatServer,再運行多個Client
設(shè)置IDEA允許運行多個實例

8.1 登錄

8.2 群聊

8.3 單聊

以上就是本文的全部內(nèi)容,希望對大家的學習有所幫助,也希望大家多多支持腳本之家。

相關(guān)文章

  • 學習Java之如何對時間進行格式化

    學習Java之如何對時間進行格式化

    當我們在默認情況下構(gòu)造出來的時間對象,它的時間格式并不適合我們閱讀,并且在開發(fā)時,pc端、Android端、iOS端等展示的時間格式可能也并不完全一樣,本文就從這幾個問題給大家介紹如何對時間進行格式化,感興趣的同學可以借鑒一下
    2023-05-05
  • Java 條件控制與循環(huán)控制實例

    Java 條件控制與循環(huán)控制實例

    下面小編就為大家?guī)硪黄狫ava 條件控制與循環(huán)控制實例。小編覺得挺不錯的,現(xiàn)在就分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2017-05-05
  • Intellij idea下使用不同tomcat編譯maven項目的服務(wù)器路徑方法詳解

    Intellij idea下使用不同tomcat編譯maven項目的服務(wù)器路徑方法詳解

    今天小編就為大家分享一篇關(guān)于Intellij idea下使用不同tomcat編譯maven項目的服務(wù)器路徑方法詳解,小編覺得內(nèi)容挺不錯的,現(xiàn)在分享給大家,具有很好的參考價值,需要的朋友一起跟隨小編來看看吧
    2019-02-02
  • 如何實現(xiàn)nohup?java進程號一直在變方法步驟詳解

    如何實現(xiàn)nohup?java進程號一直在變方法步驟詳解

    這篇文章主要為大家介紹了如何實現(xiàn)nohup?java進程號一直在變方法步驟詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2023-11-11
  • mybatis項目實現(xiàn)動態(tài)表名的三種方法

    mybatis項目實現(xiàn)動態(tài)表名的三種方法

    有時在開發(fā)過程中java代碼中的表名和數(shù)據(jù)庫的表名并不是一致的,此時我們就需要動態(tài)的設(shè)置表名,本文主要介紹了mybatis項目實現(xiàn)動態(tài)表名的三種方法,具有一定的參考價值,感興趣的可以了解一下
    2024-01-01
  • PL/SQL實現(xiàn)JAVA中的split()方法的例子

    PL/SQL實現(xiàn)JAVA中的split()方法的例子

    這篇文章主要介紹了PL/SQL實現(xiàn)JAVA中的split()方法的例子的相關(guān)資料,非常不錯,具有參考借鑒價值,需要的朋友可以參考下
    2016-07-07
  • Springboot靜態(tài)資源的訪問方法介紹

    Springboot靜態(tài)資源的訪問方法介紹

    最近在做SpringBoot項目的時候遇到了“白頁”問題,通過查資料對SpringBoot訪問靜態(tài)資源做了總結(jié),文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧
    2022-08-08
  • 在java中判斷兩個浮點型(float)數(shù)據(jù)是否相等的案例

    在java中判斷兩個浮點型(float)數(shù)據(jù)是否相等的案例

    這篇文章主要介紹了在java中判斷兩個浮點型(float)數(shù)據(jù)是否相等的案例,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2020-10-10
  • 詳解Spring MVC 集成EHCache緩存

    詳解Spring MVC 集成EHCache緩存

    本篇文章主要介紹了詳解Spring MVC 集成EHCache緩存,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2017-05-05
  • Spring中的依賴注入DI詳解

    Spring中的依賴注入DI詳解

    這篇文章主要介紹了Spring中的依賴注入DI詳解,組件之間依賴關(guān)系由容器在運行期決定,形象的說,即由容器動態(tài)的將依賴關(guān)系注入到組件之中,依賴注入的目的并非為軟件系統(tǒng)帶來更多功能,是為了提升組件重用的頻率,并為系統(tǒng)搭建一個靈活、可擴展的平臺,需要的朋友可以參考下
    2024-01-01

最新評論