嚴格意義上來講,狀態機理論應該屬于控制理論的范疇,他其實不光在軟件領域發光發熱,實際上他對于硬件設計更加的重要,多年前我曾讀過分享過那些當年看不懂的文章,依舊給他人很大的幫助。
有興趣的童鞋可以去讀一下,不論你從事軟件還是硬件,都值得一讀,接下來進入正題,我們來速成狀態機,舉個例子:
早期的狀態機控制理論(不完整)
地震啦~!!!! 我:。。。跑~!!!(這就是狀態機的早期的事件動作范型)(缺點:我是誰 ,我在哪 ,我為什么要跑?)
完整的狀態機模型(完整語義)
地震啦~!!!
版本一,我:我居然在大樓里~! 跑~!!!
版本二,我:我在大草原上~!沒事兒~!!!
這就是完整的狀態機模型(事件-狀態-動作范型),看到這里你也就學會了狀態機,簡不簡單~!是的,狀態機的初衷就是為了不制造麻煩~!
狀態機進階(任何理論都會因實踐慢慢改進豐富和進階):
普通版狀態機:
媽媽要出門買雞蛋了,你在家先寫十分鐘的作業,然后就可以看會兒動畫片了, 這時候你躁動了,十分鐘等于六百秒,于是開始1...2...3...600....終于可以看電視了,你再數數之前,要先想一下之前數的是幾(歷史就是狀態),然后才知道下一個是幾。要完整這件事你要數600個數,轉換600中狀態,什么時候轉換呢,你會盯著時鐘的秒表,他動一下,你加一(事件)。結果媽媽回來,發現你居然沒有寫作業,于是不光挨了罵,動畫片也看不成了。
擴展狀態機(進階版):
媽媽要出門買雞蛋了,你在家先寫十分鐘的作業,然后就可以看會兒動畫片了, 你拿過鬧鐘,定了一個十分鐘的鬧鐘,然后繼續寫作業(狀態1),十分鐘后,鬧鐘響了(監護條件),時間到啦,你放下作業,打開電視,開始看動畫片(狀態2),不一會兒媽媽回來了,檢查了你的作業,發現你很守信用,于是不光讓你多看一會兒電視,而且還獎勵了一根棒棒糖。
總結:并不是所有的狀態都要被構造成狀態機,如果有很多狀態其實都是一個簡單的變量維護,那么可以建立一個狀態機,再其內部維護這個變量,創建一個監護條件,只有等監護條件滿足時,才跳轉到其它狀態機。
注意:在單片機軟件中構造一個狀態機是需要一定內存資源開銷的,想想我們那可憐的RAM,一個項目到底要分解成多少個狀態機不光是技術問題,更是藝術問題。
狀態機中最重要的幾個概念:事件 狀態 動作 (擴展狀態機還有監護條件)
一個簡單的狀態機可以如下描述:
狀態機還有個很重要的概念要RTC(Run-to-Completion):大體意思是運行到完成,這個過程是不可以打斷的,因為如果被打斷了,那么你就恢復現場,問題就復雜了,舉個例子,鬧鐘響了(事件發生),我(睡眠狀態)到(起床狀態)需要完成的RTC如下:
伸懶腰 穿衣 穿鞋 洗漱結束。假如你在穿衣的過程中,突然接到女神的求助電話,這時候可能直接從床上跳起來,寫也顧不上穿就飛奔而去,這就打亂了我們原本的狀態機執行上下文,導致你鞋沒穿 牙沒刷出門了,理論上這是不允許的,盡管現實中是你想要的。
到這里基本就完成了傳統意義上的FSM(有限狀態機)的學習,理論的東西,理解就好了,詳細看書可以要花個半天,當然更專業,如下: