0

私はブーストの非同期ステートチャートを使ってプログラムを書いています。このプログラムでは、非同期シリアル ポートを使用して別のデバイスと通信します。シリアルポート経由でデバイスからの確認を待ってから、「確認を受信しました」イベントを投稿する状態があります。これはうまくいきますが、「タイムアウト」イベントも実装したいと思います。

以前のプログラムでは、ループが実行されるたびに実行できるコードがあるステート マシンに switch case ステートメントを使用していました。これは、コードを実行して、何かがタイムアウトしたために状態を変更する必要があるかどうかを確認できることを意味しました。このような:

while(1){
    switch (state){
        case 0:{
            sendMessage();
            state = 1;
            sendTime = boost::chrono::steady_clock::now();
        }
        break;
        case 1:{
            if (isConfirmationReceived()){
                // do something
                state = 2;
            }
            else if (boost::chrono::steady_clock::now() > sendTime + boost::chrono::duration<double>(WAIT_LENGTH)){
                //raise a time out error
                state = 3;
            }
        }
        break;
        // etc etc

    }
}

boost::StateChart を使用してこのようなものを実装するにはどうすればよいですか? これについては、まったく別の方法で考えるべきですか?

4

1 に答える 1

0

これがベスト プラクティスかどうかはわかりませんが、SMEvTickイベントを定期的に (1 ミリ秒程度) 送信し、スーパー状態でイベントを処理することで、この問題を解決しました。ClearTimeout() SetTimeout()また、DisableTimeout()メンバー関数を追加して、次のようにアクセスすることもできます。

context< TimeoutSuperState >().SetTimeout(1000);

タイムアウト時にスーパーステートをエラー状態に移行させるか、EvOnTimeout状態に応じて異なる方法で処理できる SM に送信できます。

于 2013-06-28T18:00:39.037 に答える