Java使用Socket簡(jiǎn)單通訊詳解
Java實(shí)現(xiàn)基于Socket的簡(jiǎn)單通信
一.ServerSocket
1.使用JavaFX寫(xiě)的小界面,方便觀察客戶(hù)端連接情況
TextArea ta = new TextArea(); Scene scene = new Scene(new javafx.scene.control.ScrollPane(ta), 450, 200); primaryStage.setTitle("Server"); primaryStage.setScene(scene); primaryStage.show();
2.創(chuàng)建ServerSocket并處理客戶(hù)端連接并顯示客戶(hù)端基本信息
兩個(gè)客戶(hù)端連接后進(jìn)行通信,未能實(shí)現(xiàn)動(dòng)態(tài)處理。
new Thread(() -> { try { ServerSocket serverSocket = new ServerSocket(8000); Platform.runLater(() -> { ta.appendText(new Date() + " : Server started at " + "\n"); ta.appendText(new Date() + " : wait to persons to join the chat" + "\n"); }); while (true){ Socket person1 = serverSocket.accept(); number++; InetAddress inetAddress1 = person1.getInetAddress(); Platform.runLater(() -> { ta.appendText(new Date() + ": Person" + number + "joined the chat" + "\n"); ta.appendText(new Date() + ": Person" + number + "'s host name is " + inetAddress1.getHostName() + "\n"); ta.appendText(new Date() + ": Person" + number + "'s host address is " + inetAddress1.getHostAddress() + "\n"); ta.appendText(new Date() + ": wait for Person2 " + "\n"); }); Socket person2 = serverSocket.accept(); number++; InetAddress inetAddress2 = person2.getInetAddress(); Platform.runLater(() -> { ta.appendText(new Date() + ": Person" + number + "joined the chat" + "\n"); ta.appendText(new Date() + ": Person" + number + "'s host name is " + inetAddress2.getHostName() + "\n"); ta.appendText(new Date() + ": Person" + number + "'s host address is " + inetAddress2.getHostAddress() + "\n"); ta.appendText(new Date() + ": Start the chat " + "\n"); }); new Thread(new HandleChat(person1,person2)).start(); try { Thread.sleep(100); } catch (InterruptedException e) { e.printStackTrace(); } } } catch (IOException e) { e.printStackTrace(); } }).start();
3.新建Handle類(lèi)處理接收發(fā)送兩個(gè)客戶(hù)端的消息
只實(shí)現(xiàn)了一人一句的效果,沒(méi)有實(shí)現(xiàn)一人連續(xù)發(fā)送消息對(duì)方也能正確接收。
class HandleChat implements Runnable{ Socket person1; Socket person2; public HandleChat(Socket person1,Socket person2){ this.person1 = person1; this.person2 = person2; } @Override public void run() { try { DataInputStream fromPerson1 = new DataInputStream(person1.getInputStream()); DataOutputStream toPerson1 = new DataOutputStream(person1.getOutputStream()); DataInputStream fromPerson2 = new DataInputStream(person2.getInputStream()); DataOutputStream toPerson2 = new DataOutputStream(person2.getOutputStream()); while (true){ String passage1 = fromPerson1.readUTF(); toPerson2.writeUTF(passage1); String passage2 = fromPerson2.readUTF(); toPerson1.writeUTF(passage2); } } catch (IOException e) { e.printStackTrace(); } } }
思考后將HandleChat類(lèi)中對(duì)兩個(gè)客戶(hù)端的接收發(fā)送消息處理放在兩個(gè)線程中,就可以實(shí)現(xiàn)兩個(gè)客戶(hù)端自由通信。
new Thread(() -> { while (true) { try { String passage2 = fromPerson2.readUTF(); toPerson1.writeUTF(passage2); } catch (IOException e) { e.printStackTrace(); } } }).start(); new Thread(() -> { while (true) { try { String passage1 = fromPerson1.readUTF(); toPerson2.writeUTF(passage1); } catch (IOException e) { e.printStackTrace(); } } }).start();
二.Socket
1.同樣的編寫(xiě)一個(gè)客戶(hù)端界面
BorderPane pane = new BorderPane(); pane.setPadding(new Insets(5)); pane.setStyle("-fx-border-color: green"); pane.setLeft(new Label("Enter a radius: ")); TextField tf = new TextField(); tf.setAlignment(Pos.BASELINE_RIGHT); pane.setCenter(tf); BorderPane mainPane = new BorderPane(); TextArea ta = new TextArea(); mainPane.setCenter(new ScrollPane(ta)); mainPane.setTop(pane); Scene scene = new Scene(mainPane,450,200); primaryStage.setTitle("Client"); primaryStage.setScene(scene); primaryStage.show();
2.創(chuàng)建Socket連接客戶(hù)端并獲取輸入輸出流
try { // 創(chuàng)建一個(gè)連接服務(wù)器端的Socket Socket socket = new Socket("localhost",8000); // 獲得輸入輸出流 toServer = new DataOutputStream(socket.getOutputStream()); fromServer = new DataInputStream(socket.getInputStream()); } catch (IOException e) { e.printStackTrace(); }
3.添加編輯框監(jiān)聽(tīng)處理消息發(fā)送
// 編輯框事件監(jiān)聽(tīng) tf.setOnAction(e ->{ String passage = tf.getText().trim(); tf.clear(); try { toServer.writeUTF(passage); toServer.flush(); ta.appendText("Me " + ": " + passage + "\n"); } catch (IOException e1) { e1.printStackTrace(); } });
4.創(chuàng)建新線程從服務(wù)器上接收消息
// 新線程從服務(wù)器讀取信息 new Thread(() -> { while (true) { try { String passage = fromServer.readUTF(); ta.appendText("He : " + passage + "\n"); } catch (IOException e) { e.printStackTrace(); } } }).start();
三.測(cè)試
四.總結(jié)
1.原理流程
2.不足之處
只是簡(jiǎn)單實(shí)現(xiàn)了靜態(tài)兩客戶(hù)端聊天的功能,并且只能夠第一個(gè)鏈接上的用戶(hù)先發(fā)送消息,且一人發(fā)送消息后只能等待接收另一個(gè)人的消息后才能再次發(fā)送消息。之后的時(shí)間希望能加以改進(jìn)。
到此這篇關(guān)于Java使用Socket簡(jiǎn)單通訊詳解的文章就介紹到這了,更多相關(guān)Java使用Socket簡(jiǎn)單通訊內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Java實(shí)現(xiàn)PDF轉(zhuǎn)為線性PDF詳解
線性化PDF文件是PDF文件的一種特殊格式,可以通過(guò)Internet更快地進(jìn)行查看。本文將通過(guò)后端Java程序?qū)崿F(xiàn)將PDF文件轉(zhuǎn)為線性化PDF。感興趣的可以了解一下2021-12-12Java中不得不知的Collection接口與Iterator迭代器
這篇文章主要介紹了Java中的Collection接口與Iterator迭代器,文中有詳細(xì)的代碼示例供大家參考,對(duì)我們的學(xué)習(xí)或工作有一定的幫助,需要的朋友可以參考下2023-06-06詳細(xì)分析Java并發(fā)集合LinkedBlockingQueue的用法
這篇文章主要介紹了詳細(xì)分析Java并發(fā)集合LinkedBlockingQueue的用法,小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2018-04-04三種java編程方法實(shí)現(xiàn)斐波那契數(shù)列
這篇文章主要為大家詳細(xì)介紹了三種java編程方法實(shí)現(xiàn)斐波那契數(shù)列,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2018-02-02Java C++題解leetcode 1684統(tǒng)計(jì)一致字符串的數(shù)目示例
這篇文章主要為大家介紹了Java C++題解leetcode 1684統(tǒng)計(jì)一致字符串的數(shù)目示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-01-01