『Linux_網絡』 基于狀態機的Connect斷線重連

????????客戶端會面臨服務器崩潰的情況, 我們可以試著寫一個客戶端重連的代碼, 模擬并理
解一些客戶端行為, 比如游戲客戶端等。

? ? ? ? 客戶端部分,我們本次采用狀態機的設計模式實現

下面是關于狀態機模式的介紹

狀態機模式

狀態機模式(State Pattern)是一種行為設計模式,它能讓對象在內部狀態發生改變時,改變自身的行為,給人一種對象仿佛改變了類的感覺。下面從多個方面對其進行詳細介紹。

模式動機

在軟件開發里,某些對象的行為會依據其狀態的不同而改變。若用大量的條件語句(如?if-else?或?switch-case)來處理這些狀態和行為,代碼會變得復雜、難以維護和擴展。狀態機模式把狀態的行為封裝在不同的狀態類中,將狀態轉換邏輯和對象的其他行為分離,讓代碼結構更清晰,提升了可維護性和可擴展性。

模式結構

狀態機模式主要包含以下幾個角色:

  1. 上下文(Context):擁有一個狀態對象的引用,負責與客戶端交互,依據不同的情況調用狀態對象的方法,并且能夠在狀態之間進行轉換。
  2. 抽象狀態(State):定義了一個接口,該接口包含了所有可能的狀態行為,所有具體狀態類都要實現這個接口。
  3. 具體狀態(Concrete State):實現了抽象狀態接口,具體實現了在該狀態下的行為,并且在必要時可以改變上下文的狀態。

優點

  • 可維護性:狀態的行為被封裝在不同的類中,使得代碼的維護和擴展更加容易。
  • 可擴展性:如果需要添加新的狀態,只需要創建一個新的具體狀態類并實現相應的行為即可。
  • 狀態轉換清晰:狀態轉換邏輯集中在上下文類中,使得狀態轉換更加清晰和易于管理。

缺點

  • 類數量增加:如果狀態較多,會導致類的數量增加,增加了系統的復雜度。
  • 狀態轉換邏輯復雜:如果狀態轉換邏輯復雜,上下文類中的狀態轉換代碼可能會變得復雜。

文檔編輯器樣例

下面給一個給一個文件編輯器的樣例,來幫助理解

假設你正在開發一個文檔編輯器,文檔有三種狀態:草稿(Draft)、審核中(Review)和已發布(Published)。文檔在不同的狀態下有不同的行為,比如草稿狀態可以編輯和提交審核,審核中狀態可以通過審核或者打回草稿,已發布狀態可以查看但不能編輯。

#include <iostream>// 前向聲明
class Document;// 抽象狀態類
class DocumentState {
public:virtual void edit(Document* document) {}virtual void submit(Document* document) {}virtual void approve(Document* document) {}virtual void reject(Document* document) {}virtual void view(Document* document) {}virtual ~DocumentState() {}
};// 具體狀態:草稿
class DraftState : public DocumentState {
public:void edit(Document* document) override {std::cout << "文檔處于草稿狀態,可以編輯。" << std::endl;}void submit(Document* document) override;
};// 具體狀態:審核中
class ReviewState : public DocumentState {
public:void approve(Document* document) override;void reject(Document* document) override;
};// 具體狀態:已發布
class PublishedState : public DocumentState {
public:void view(Document* document) override {std::cout << "文檔已發布,可以查看。" << std::endl;}
};// 上下文:文檔
class Document {
private:DocumentState* state;
public:Document();~Document();void setState(DocumentState* newState);void edit();void submit();void approve();void reject();void view();
};// DraftState 類的 submit 方法實現
void DraftState::submit(Document* document) {std::cout << "文檔已提交審核。" << std::endl;document->setState(new ReviewState());
}// ReviewState 類的 approve 方法實現
void ReviewState::approve(Document* document) {std::cout << "文檔審核通過,已發布。" << std::endl;document->setState(new PublishedState());
}// ReviewState 類的 reject 方法實現
void ReviewState::reject(Document* document) {std::cout << "文檔審核未通過,打回草稿。" << std::endl;document->setState(new DraftState());
}// Document 類的構造函數
Document::Document() {state = new DraftState();
}// Document 類的析構函數
Document::~Document() {delete state;
}// Document 類的 setState 方法
void Document::setState(DocumentState* newState) {delete state;state = newState;
}// Document 類的 edit 方法
void Document::edit() {state->edit(this);
}// Document 類的 submit 方法
void Document::submit() {state->submit(this);
}// Document 類的 approve 方法
void Document::approve() {state->approve(this);
}// Document 類的 reject 方法
void Document::reject() {state->reject(this);
}// Document 類的 view 方法
void Document::view() {state->view(this);
}int main() {Document document;document.edit();document.submit();document.approve();document.view();return 0;
}    

Connect 斷線重連具體實現

Connect.hpp

?

?Client.cc

?測試Debug

測試部分,我采用我們在Linux網絡篇Tcp章節所編寫的翻譯服務器測試以及將實現客戶端與服務器通信的代碼放入process中

?編譯運行,服務器和客戶端之間就可以進行通信了

斷掉服務器,再啟動服務器,重新連接的服務也是支持的?

但是我們發現每次與服務器通信,都會有一個connect success... 的提示語,那么我們怎么去掉它呢?

?首先,我們需要明確為什么每次通信都會打印這個信息

這是因為,我們服務器與客戶端之間的通信循環走的是外面的這個狀態判斷,當狀態為CONNECTED的時候,我們正常執行process代碼,但當第二次循環的時候,由于我們連接狀態一直是成功的,所以再執行這里的時候,還是會打印這條信息,那我們應該怎么辦呢?

有兩種方法,第一種在設計一種狀態,就是當連接建立成功的時候,就只執行process,而不去打印這條提示語。

還記得我們之間設計的Connceting狀態嗎,當時說的可有可無,在這里我們就可以利用這個狀態,而不用去在取名一個新的狀態了。

像這樣

每次進入process,就設置狀態正在連接中。

在狀態循環中添加這樣的一條判斷

編譯運行,發現就沒有這樣的提示了

?

同樣也是支持斷線重連的?

?

但是這個方法也體現了狀態機的一個缺點,就是狀態數量的增加,狀態之間的復雜性問題。

第二種方法,就是將外面的循環挪到process中,這樣就不需要借助于狀態判斷的循環來維持服務器與客戶端之間的通信了?。

實現很簡單,就是在Process內部加一個循環循環條件是當前狀態為connected,修改狀態的時候,就可以自動退出了

?

編譯運行,各種功能也是支持的

?


?至此,我們的基于狀態機實現Client斷線重連,就結束了。

如有什么問題,歡迎評論區留言提問。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/bicheng/79932.shtml
繁體地址,請注明出處:http://hk.pswp.cn/bicheng/79932.shtml
英文地址,請注明出處:http://en.pswp.cn/bicheng/79932.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

5月6日日記

一點心得是 看通知要仔細認真&#xff0c;自己想問的問題要先看看通知或者文件中說了沒有&#xff0c;如果沒說再去問相關負責人。 上課的教室一定要看好&#xff0c;看準了再去。別像今天一樣先去了科技樓又去了工學館。 線代開課了。感覺總體還行&#xff0c;并不是很難。…

【算法專題十】哈希表

文章目錄 0.哈希表簡介1. 兩數之和1.1 題目1.2 思路1.3 代碼 2.判斷是否為字符重排2.1 題目2.2 思路2.3 代碼 3. leetcode.217.存在重復元素3.1 題目3.2 思路3.3 代碼 4. leetcode.219.存在重復的元素Ⅱ4.1 題目4.2 思路4.3 代碼 5. leetcode.49.字母異位詞分組5.1 題目5.2 思路…

【前綴和】矩陣區域和

文章目錄 1314. 矩陣區域和解題思路1314. 矩陣區域和 1314. 矩陣區域和 ? 給你一個 m x n 的矩陣 mat 和一個整數 k ,請你返回一個矩陣 answer ,其中每個 answer[i][j] 是所有滿足下述條件的元素 mat[r][c] 的和: i - k <= r <= i + k, j - k <= c <= j + k …

MyBatis的SQL映射文件中,`#`和`$`符號的區別

在MyBatis的SQL映射文件中,#和$符號用于處理SQL語句中的參數替換,但它們的工作方式和使用場景有所不同。 #{} 符號 預編譯參數:#{} 被用來作為預編譯SQL語句的占位符。這意味著MyBatis會將你傳入的參數設置為PreparedStatement的參數,從而防止SQL注入攻擊,并允許MyBatis對…

Linux中為某個進程臨時指定tmp目錄

起因&#xff1a; 在linux下編譯k8s&#xff0c;由于編譯的中間文件太多而系統的/tmp分區設置太小&#xff0c;導致編譯失敗&#xff0c;但自己不想或不能更改/tmp分區大小&#xff0c;所以只能通過其他方式解決。 現象&#xff1a; tmp分區大小&#xff1a; 解決方法&#x…

Tomcat中Web應用程序停止時為了防止內存泄漏,JDBC驅動程序被強制取消注冊出現原因

1.問題描述 本地Windows環境開發的Springboot項目同樣的mysql版本&#xff0c;jdk版本&#xff0c;tomcat版本&#xff0c;本地運行沒有任何問題&#xff0c;發布到阿里云服務器上時報以下問題&#xff1a; 06-May-2025 20:06:12.842 警告 [main] org.apache.catalina.loader…

主流國產大模型(以華為盤古大模型和騰訊混元大模型為例)API調用接口的具體參數和使用方法,包括Python和C++的示例代碼

以下是主流國產大模型&#xff08;以華為盤古大模型和騰訊混元大模型為例&#xff09;API調用接口的具體參數和使用方法&#xff0c;包括Python和C的示例代碼。 華為盤古大模型 API參數&#xff1a; - model&#xff1a;模型名稱&#xff0c;如pangu-nlp-large。 - messages&…

高效調用京東 API 實戰:商品詳情頁實時數據采集接口開發指南?

在當今數字化商業環境中&#xff0c;電商數據的實時獲取與分析對于企業的決策制定和市場競爭力提升至關重要。京東作為國內領先的電商平臺&#xff0c;提供了豐富的 API 接口&#xff0c;允許開發者高效地獲取商品詳情頁的實時數據。本文將詳細介紹如何通過實戰開發&#xff0c…

MFC自定義控件開發與使用指南

MFC自定義控件開發與使用指南 自定義控件、雙緩沖 1. 概述 MFC(Microsoft Foundation Classes)框架提供了豐富的內置控件,但在實際開發中,我們常常需要創建自定義控件來滿足特定的界面需求。本文將詳細介紹如何在MFC中開發自定義控件,并以CCustomTextControl為例,展示自…

第100+40步 ChatGPT學習:R語言實現多輪建模

回顧一下什么叫多輪建模&#xff1a; 要綜合判斷一個模型好不好&#xff0c;一次隨機抽樣是不行的&#xff0c;得多次抽樣建模&#xff0c;看看整體的性能如何才行&#xff08;特別是對于這種小訓練集&#xff09;。 所以我的思路是&#xff0c;隨機抽取訓練集和驗證集2000次…

編碼器型與解碼器型語言模型的比較

編碼器型與解碼器型語言模型的比較 1. 引言 自然語言處理&#xff08;NLP&#xff09;領域近年來取得了革命性進展&#xff0c;這在很大程度上歸功于基于Transformer架構的語言模型。在這一技術生態中&#xff0c;編碼器型&#xff08;Encoder-only&#xff09;和解碼器型&am…

python--------修改桌面文件內容

目錄 1. 文件的讀寫1. 寫入文件2. 讀取文件3. 追加內容到文件 2.file_path 的常見方法1. 絕對路徑2. 相對路徑3. 使用 os.path 模塊構建路徑5. 路徑操作5. 用戶主目錄路徑 4. 修改文件內容1.將修改后的內容寫回文件2. 逐行處理文件內容3. 使用上下文管理器確保文件安全 1. 文件…

愛普生VG7050EFN壓控晶振在小基站的應用優勢

在 5G 通信時代&#xff0c;小基站作為提升網絡覆蓋和容量的重要一環&#xff0c;小基站的穩定運行對于保障用戶流暢的通信體驗起著關鍵作用。而在小基站的核心組件中&#xff0c;時鐘信號源的質量直接影響著通信質量和設備性能。愛普生VG7050EFN晶振憑借其高性能、小尺寸和低功…

人工智能如何革新數據可視化領域?探索未來趨勢

在當今數字化時代&#xff0c;數據如同洶涌浪潮般不斷涌現。據國際數據公司&#xff08;IDC&#xff09;預測&#xff0c;全球每年產生的數據量將從 2018 年的 33ZB 增長到 2025 年的 175ZB。面對如此海量的數據&#xff0c;如何有效理解和利用這些數據成為了關鍵問題。數據可視…

精益數據分析(42/126):移動應用商業模式的深度剖析與實戰要點

精益數據分析&#xff08;42/126&#xff09;&#xff1a;移動應用商業模式的深度剖析與實戰要點 在創業和數據分析的學習之路上&#xff0c;我們持續探索不同商業模式的奧秘&#xff0c;今天聚焦于移動應用商業模式。我希望和大家一起進步&#xff0c;深入解讀《精益數據分析…

未來 CSS:變量、容器查詢與新特性的探索

引言&#xff1a;CSS 演進與未來展望 在前端開發的快速發展浪潮中&#xff0c;CSS 已從簡單的樣式標記語言蛻變為構建現代設計系統的強大基礎。根據 HTTP Archive 的 Web Almanac 的調查&#xff0c;超過 86% 的網站已采用至少一項現代 CSS 特性&#xff0c;這一數字仍在持續攀…

概統期末復習--速成

隨機事件及其概率 加法公式 推三個的時候ABC&#xff0c;夾逼準則 減法準則 除法公式 相互獨立定義 兩種分析 兩個解法 古典概型求概率&#xff08;排列組合&#xff09; 分步相乘、分類相加 全概率公式和貝葉斯公式 兩階段問題 第一個小概率*A在小概率的概率。。。累計 …

論微服務架構設計及應用

目錄 摘要(300~330字) 正文(2000~2500字,2200字為宜) 背景介紹(500字做左右) 論點論據(1500字做左右)

【東楓科技】AMD / Xilinx Alveo? V80計算加速器卡

AMD / Xilinx Alveo? V80計算加速器卡 AMD/Xilinx Alveo ? V80計算加速器卡是一款功能強大的計算加速器&#xff0c;基于7nm Versal? 自適應SoC架構而打造。 AMD/Xilinx Alveo V80卡設計用于內存密集型任務。 這些任務包括HPC、數據分析、網絡安全、傳感器處理、計算存儲和…

基于大模型的自然臨產陰道分娩全流程預測與方案研究報告

目錄 一、引言 1.1 研究背景與目的 1.2 研究意義 1.3 國內外研究現狀 二、大模型技術原理與應用概述 2.1 大模型基本原理 2.2 在醫療領域的應用現狀 2.3 用于分娩預測的優勢 三、術前預測與準備方案 3.1 產婦身體狀況評估指標 3.2 大模型預測流程與方法 3.3 基于預…