2013-08-20 100 views
0

我工作的一個有限狀態機庫,這些公共方法:聲明,異常,運行時錯誤或未定義行爲?

template <typename STATE_T> 
void add_state();    // allocate STATE_T on heap - STATE_T must derive from state 

template <typename FROM_STATE_T, typename TO_STATE_T> 
void link_state(std::function<bool()> cond, unsigned int priority); 

// search for base state pointer that can be dynamically caste d to STATE_T* type, set this state as the beginning state 
template <typename STATE_T> 
void begin_state(); 

void execute(); 

//STATE_T must be a user defined state class that inherits from the base state class. 

我選擇在編譯時運行時實現,因爲使用可變參數模板參數的狀態時,界面會更復雜。但是,我想強制實施一些限制,以確保程序員在實現狀態機時不會引入錯誤。

這裏有限制,我想執行:

  1. 不能添加重複的狀態
  2. 無法鏈接不存在的狀態(如狀態類型(即增加了兩個相同的派生型。)沒有國家的FSM列表)
  3. 國家必須有一個入口點/可到達
  4. 一個開始和結束時的必須存在
  5. 執行不能同時運行多次

聲明中止程序並明確遵守這些約束,但它是正確的選擇嗎?

可能違反了1,2,3並且fsm仍然處於有效狀態(根本不做任何事情),但我不喜歡隱式處理這些問題的想法,因爲它引入了虛假的安全感隱藏程序員錯誤。

如果我爲1,2,3引發異常並且程序員捕獲它們,那麼fsm仍然可以處於有效狀態,從而允許運行不正常的fsm。

5是不應該做的事情。我應該處理這個問題,還是把它作爲UB?

什麼是最適合這些約束的機制?

回答

2

這是一個相當典型的處理錯誤的問題。答案通常取決於成本。這個問題的成本是什麼被忽視?程序異常終止的成本是多少?

在大多數情況下,程序崩潰的代價並不是很大。用戶將重新啓動它。在這種情況下,你應該去處理未處理的異常。這樣,你會注意到這些bug很快,修復它們,最終得到一個更好的程序。有一種混合方法:在DEBUG構建中,通過「斷言失敗」消息框(通常這是用ASSERT()宏)來處理錯誤,但是在發佈版本中,靜靜地處理錯誤。然而,這會讓問題在客戶端的計算機上不被注意,往往會引發其他錯誤,這些錯誤很難找到。

最後,關於程序員可以處理異常的擔憂:這不是你應該考慮的問題。你指出了一個致命的錯誤,如果程序員忽略它,那是他的錯。

相關問題