Как читать схему FSM - PullRequest
       18

Как читать схему FSM

5 голосов
/ 21 июля 2011

FMS

Как мне взять эту диаграмму и перевести ее в полезную программу. Я не совсем уверен, как читать эту диаграмму. Если бы кто-то мог просто рассказать мне, может быть, показать пример кода и его связь с диаграммой, это было бы здорово.

Спасибо!

1 Ответ

10 голосов
/ 21 июля 2011

Круги с текстом внутри являются состояниями.Текст описывает состояние.

Пунктирная стрелка указывает на начальное состояние.

Исходящие стрелки определяют, где это состояние может измениться.Рядом со стрелкой находится текст, разделенный линией на верхнюю и нижнюю части.Нижняя часть - это действия, которые должны выполняться при переходе стрелки.Верхняя часть - это условия.Когда они истинны - этот переход выполняется (и, следовательно, нижняя часть).

Лямбда-символ означает, что вы ничего не должны делать, кроме изменения текущего состояния, когда происходит переход.

Таким образом, нижние части имеют грубую соответствующуюк вашим функциям.А верхние части - это точки, где вы должны ждать условий - опроса или асинхронного ожидания ожидающих пакетов ввода-вывода, что угодно.

Вот некоторый псевдокод, похожий на C (я написал его вот такне предполагайте, что это работает или даже компилируется):

enum State { WaitFor0Call, WaitForAck0, WaitForCall1, WaitForAck1 }

int main() {
   State state = WaitFor0Call;
   while (1) {
      switch (state) {
         case WaitFor0Call:
            if (rdt_rcv(rcvpkt)) continue;
            if (rdt_send(data)) {
               state = WaitForAck0;
               sndpkt = make_pkt(0, data, checksum);
               udt_send(sndpkt);
               start_timer();
            }
            break;
         case WaitForAck0:
            // ...similar code...
            break;
         case WaitForCall1:
            // ...similar code...
            break;
         case WaitForAck1:
            // ...similar code...
            break;
      }
   }
}

Следует также учитывать, что функции приема и отправки могут блокировать, поэтому код if (rdt_rcv(rcvpkt)) whatever; технически неверен, так как вы не проверяете rdt_send пока не вернет контроль.Итак, FSM передает только логический поток, а не технические аспекты того, как он должен быть организован, управление потоками и т. Д. И мой код не показывает эти аспекты также потому, что он может быть довольно сложным в зависимости от ваших потребностей и потому, что вы не предоставили достаточно деталейчтобы дать информированные советы о таких вещах:)

Мое единственное предположение, что у вас будет некоторый двунаправленный поток (для ввода и вывода соответственно), и условия будут такими, как if (there_is_ready_for_consuming_packet_in_the_input_queue) continue; и if (data_was_put_to_outgoing_stream_successfully) ...;

...