В предыдущей статье рассматривалась структурная модель СКУД как совокупности ролей объектов и двойных связей между ними. Такая модель позволяет отразить результаты всех интересующих нас процессов, протекающих в системе. Процессы в системе выражаются через взаимодействия объектов, а результаты взаимодействий запоминаются в связях. Можно сказать, что связи — это память о взаимодействиях, но сами процессы взаимодействия в структурной модели никак не отражаются. Наблюдатель видит взаимодействия через изменения в поведении или изменения в состоянии объектов, которые мы будем называть устройствами. Например, при поднесении карты c RFID меткой к считывателю последний сообщает о считывании звуковым сигналом и миганием светодиода. Это может интерпретироваться как изменение состояния физического считывателя, при этом само взаимодействие между картой и считывателем, собственно чтение, не рассматривается. Предполагается, что считыватель проходит через ряд дискретных состояний. Такие дискретные состояния удобно моделировать при помощи машин состояний, но для этого нужно установить канал между физическим миром и виртуальным миром (компьютерной моделью). Такой канал, управляемый контроллером канала, передает физические сигналы от устройства, которые специальным модулем связи преобразуются в сигналы, управляющие машиной состояний устройства. Канал может быть двухсторонним:
Одно устройство может быть связано с несколькими каналами и один канал может быть связан с несколькими устройствами, при этом обслуживать все каналы может один модуль связи:
Устройствами мы называем объекты, поведение которых может быть описано набором дискретных состояний моделируемых машинами состояний. Определение набора состояний для каждого устройства осуществляется конструктором моделируемой системы.
В реализованной СКУД использовались два считывателя. Один считыватель был установлен на турникете, а второй на картоприемнике. При такой схеме расположения считывателей посетитель с разовым пропуском может покинуть зону доступа только при возврате карты через картоприемник: считыватель картоприемника сформирует статус метки Выход разрешен, а считыватель на турникете — Выход запрещен. Оба считывателя обслуживаются двумя каналами, через один канал поступает информация об имени считывателя, а по второму — об имени карты.
Поэтому у считывателя есть следующие дискретные состояния:
Использование отдельного состояния Получены имена считывателя и карты вместо совмещения его с начальным состоянием вызвано тем, что считыватель является частью системы. В этом случае возврат в начальное состояние будет осуществляться по сигналу от турникета.
Переход в эти состояния осуществляются при получении одного из сигналов: определено имя считывателя, определено имя карты, осуществлен переход или сработал таймер (сигнал от машины турникета), получена ошибка. Обозначим эти сигналы для примера следующим образом: определено имя считывателя — nr, определено имя карты — nc, получен сигнал от турникета — ts, получена ошибка — er. Так как в общем случае неизвестно, что определится раньше — имя считывателя или карты, то машина состояний с сигналами и соответствующими переходами будет иметь вид:
Машина реализована очень просто: так как новое состояние однозначно определяется текущим состоянием и сигналом, то в качестве ключа, определяющего переход берется текстовая величина состояние_сигнал. Зная начальное состояние и новое состояние легко определить и переход, который будет задаваться текстовой величиной текущее_состояние#новое_состояние.Тогда для машины считывателя мы получим следующие соответствия между ключом и новым состоянием, а также переходом:
Другими словами, сигналы и переходы в машине состояний считывателя полностью описываются вектором gen
Алгоритм работы машины состояний совершенно очевиден (первоначальное состояние задается при запуске программы):
Все действия, которые происходят при изменении состояний, осуществляются только на переходах соответствующими скриптами. Для машины считывателя эти действия приведены в таблице:
Приведенная машина используется в случае, когда считыватель работает в режиме идентификации карты посетителя для перехода через турникет. В реализованной СКУД считыватель картоприемника может работать и в режиме регистрации нового посетителя (новой карты). В этом случае взаимодействия между ним и турникетом нет, и приведенная машина работать не будет, так как она не сможет выйти из состояния 3. Чтобы машина в режиме регистрации после определения номера считывателя и номера карты возвращалась в начальное состояние ее нужно подменить на следующую:
А как же быть с тем, что из состояний 1 и 2 можно перейти по двум разным переходам (на этих переходах осуществляются разные действия)? Дадим переходам имена (на рисунке они указаны в ромбах)
Например, между состояниями 1 и 0 два перехода по сигналу nc и по сигналу er. Для единственного перехода он имел имя 1#0, для нескольких переходов будем использовать имена текущее_состояние#имя_перехода#новое_состояние.
Для того, чтобы можно было использовать алгоритм, приведенный выше, изменим правило образования имени состояния в gen[1]: имя_перехода#имя_нового_состояния. Тогда вектор gen, определяющий поведение машины будет иметь вид:
Минимальные изменения алгоритма связаны с определением нового состояния, т.к. nState=gen[1][keyInd] содержит не имя нового состояния, а его комбинацию с именем перехода, но совершенно очевидно, как его найти.
Машина в режиме регистрации на переходах выполняет другие действия, она не общается с турникетом
Турникет представляет собой «сложное» устройство, в котором есть два замка и устройство фиксирующее переход, обычно это геркон. Есть еще сигнальные лампы, показывающие состояние замков и возможно, источник звука. Один замок назовем входом, а другой — выходом. Так как каждый замок может находиться в одном из двух состояний (открыт/закрыт), то у турникета могут быть следующие состояния:
Управление турникетом осуществляется по командам считывателя, командам управляющего устройства (в нашем случае — тачскрином планшета), а также сигналу геркона. Кроме того, для того, чтобы предотвратить «зависание» системы в случае отказа от перехода (считыватель сработал, замок открылся, а посетитель не прошел), в систему добавлен таймер, который также влияет на переходы в машине турникета.
Переход в эти состояния осуществляются при получении одного из сигналов: открыть вход, открыть выход (от считывателя), закрыть вход/выход (от геркона — турникета), открыть/закрыть вход/выход (от тачскрина), закрыть вход/выход (от таймера):
Машина состояний турникета с сигналами и переходами, приведенными в таблице, будет иметь вид:
Машина турникета выполняет следующие действия на переходах:
Построенная машина турникета позволяет осуществить односторонний проход в любом направлении при регистрации карты со статусом постоянная или временная на считывателе турникета и выход посетителя с картой со статусом разовая только через ее регистрацию на считывателе картоприемника. Также возможно управление турникетом с планшета (нажатие на стрелку 1 откроет вход, а 2 — выход. Закрытие происходит по сигналам геркона и таймера):
В тоже время, периодически возникают случаи, когда необходимо открытие или закрытие входа/выхода по кнопке безотносительно к наличию карты. Для этого используются «светофоры» слева (вход) и справа (выход). Карты на входе или выходе работают только тогда, когда у соответствующего светофора «горит» желтый свет. Красный сигнал закрывает соответствующий замок и никакой картой его открыть нельзя, а зеленый — наоборот открывает и ни геркон, ни таймер его закрыть не могут.
И теперь возникает вопрос: если при нажатии на зеленую кнопку светофора мы открываем вход, т.е. осуществляем в машине турникета переход в состояние 1, то как предотвратить переход в состояние 0 по сигналу геркона gt или таймера tt? Понятно, что при «машинном» подходе не хочется рассматривать работу с флагами и т.п., а хочется работать с машиной, заданной вектором gen.
Расширим понятие ключа в векторе gen. Добавим в строку для формирование ключа величину, которую будем называть условием, т.е ключ это состояние_сигнал+условие. Определим следующие значения условия в зависимости, какой свет «горит» на светофорах и какой ключ будет для сигналов от геркона gt и таймера tt в состоянии 1:
Теперь мы знаем ответ на вопрос. После открытия входа зеленой кнопкой левого светофора сигнал от геркона создаст ключ 1_gtIs, а сигнал от таймера — 1_ttIs, которых нет в векторе gen и поэтому никакого перехода не произойдет. Турникет останется в состоянии 1.
Рассмотрим дополнительные переходы в машине турникета связанные с нажатиями на кнопки светофоров. Сигналы от светофора входа обозначим lr — красный, ly- желтый, lg — зеленый, а от светофора выхода — rr — красный, ry- желтый, rg — зеленый.
Соответствующие переходы в машине состояний:
Полный вектор gen для машины состояний турникета:
Действия на дополнительных переходах понятны из расшифровок сигнала.
Управление турникетов может осуществляться с планшета и наоборот, состояние интерфейса зависит от сигналов от считывателя и турникета.
Как видно из начального состояния интерфейса (рисунок выше) для управления используется две кнопки в виде стрелок и по три кнопки на каждом светофоре. Стрелки работают только тогда, когда на соответствующем светофоре желтый свет. Если на светофоре красный или зеленый, то стрелка не работает. Другими словами, у светофора есть состояние включен и выключен. Также по два таких же состояния есть и у стрелок.
В итоге получаем следующие возможные состояния интерфейса:
Соберем, как и ранее все сигналы и переходы в таблицу (укажем сигналы, относящиеся только к левой половине диаграммы, а вектор gen приведем полностью).
Соответствующие переходы в машине:
Полный вектор gen для машины состояний интерфейса:
Действия на переходах иллюстрируются состояниями интерфейса.
Кроме того, на переходах изменяется условие для машины турникета и происходит ее вызов (сигналы ep,xp,lr,lg,ly,rr,rg,ry):
Таким образом, мы построили при помощи трех машин состояний, синхронизирующихся при помощи обменов сигналами, простую динамическую модель СКУД, позволяющую реализовывать достаточно сложную систему управления.
В дальнейшем будет приведен живой пример реализации СКУД, основанной на принципах изложенных в этой и предыдущей статьях.
Одно устройство может быть связано с несколькими каналами и один канал может быть связан с несколькими устройствами, при этом обслуживать все каналы может один модуль связи:
Устройства в модели СКУД
Устройствами мы называем объекты, поведение которых может быть описано набором дискретных состояний моделируемых машинами состояний. Определение набора состояний для каждого устройства осуществляется конструктором моделируемой системы.
Машина состояний считывателя
В реализованной СКУД использовались два считывателя. Один считыватель был установлен на турникете, а второй на картоприемнике. При такой схеме расположения считывателей посетитель с разовым пропуском может покинуть зону доступа только при возврате карты через картоприемник: считыватель картоприемника сформирует статус метки Выход разрешен, а считыватель на турникете — Выход запрещен. Оба считывателя обслуживаются двумя каналами, через один канал поступает информация об имени считывателя, а по второму — об имени карты.
Поэтому у считывателя есть следующие дискретные состояния:
- считыватель готов к получению сигналов;
- получен имя считывателя;
- получено имя карты;
- получены имена считывателя и карты.
Использование отдельного состояния Получены имена считывателя и карты вместо совмещения его с начальным состоянием вызвано тем, что считыватель является частью системы. В этом случае возврат в начальное состояние будет осуществляться по сигналу от турникета.
Переход в эти состояния осуществляются при получении одного из сигналов: определено имя считывателя, определено имя карты, осуществлен переход или сработал таймер (сигнал от машины турникета), получена ошибка. Обозначим эти сигналы для примера следующим образом: определено имя считывателя — nr, определено имя карты — nc, получен сигнал от турникета — ts, получена ошибка — er. Так как в общем случае неизвестно, что определится раньше — имя считывателя или карты, то машина состояний с сигналами и соответствующими переходами будет иметь вид:
Машина реализована очень просто: так как новое состояние однозначно определяется текущим состоянием и сигналом, то в качестве ключа, определяющего переход берется текстовая величина состояние_сигнал. Зная начальное состояние и новое состояние легко определить и переход, который будет задаваться текстовой величиной текущее_состояние#новое_состояние.Тогда для машины считывателя мы получим следующие соответствия между ключом и новым состоянием, а также переходом:
Состояние | Сигнал | Расшифровка сигнала | Ключ | Состояние | Переход |
0 | nr | Имя считывателя | 0_nr | 1 | 0#1 |
0 | nc | Имя карты | 0_nc | 2 | 0#2 |
1 | nc | Имя карты | 1_nc | 3 | 1#3 |
1 | er | Ошибка | 1_er | 0 | 1#0 |
2 | nr | Имя считывателя | 2_nr | 3 | 2#3 |
2 | er | Ошибка | 2_er | 0 | 2#0 |
3 | ts | Сигнал турникета | 3_ts | 0 | 3#0 |
Другими словами, сигналы и переходы в машине состояний считывателя полностью описываются вектором gen
gen=[[0_nr, 0_nc, 1_nc, 1_er, 2_nr, 2_er, 3_ts], [1, 2, 3, 0, 3, 0, 0]]
Алгоритм работы машины состояний совершенно очевиден (первоначальное состояние задается при запуске программы):
Все действия, которые происходят при изменении состояний, осуществляются только на переходах соответствующими скриптами. Для машины считывателя эти действия приведены в таблице:
Переход | Действия |
0#1 | Определение имени считывателя в системе |
0#2 | Определение имени карты в системе |
1#3, 2#3 | Вызов машины турникета (сигналы eo, xo) |
1#0, 2#0, 3#0 | Действий нет |
Приведенная машина используется в случае, когда считыватель работает в режиме идентификации карты посетителя для перехода через турникет. В реализованной СКУД считыватель картоприемника может работать и в режиме регистрации нового посетителя (новой карты). В этом случае взаимодействия между ним и турникетом нет, и приведенная машина работать не будет, так как она не сможет выйти из состояния 3. Чтобы машина в режиме регистрации после определения номера считывателя и номера карты возвращалась в начальное состояние ее нужно подменить на следующую:
А как же быть с тем, что из состояний 1 и 2 можно перейти по двум разным переходам (на этих переходах осуществляются разные действия)? Дадим переходам имена (на рисунке они указаны в ромбах)
Например, между состояниями 1 и 0 два перехода по сигналу nc и по сигналу er. Для единственного перехода он имел имя 1#0, для нескольких переходов будем использовать имена текущее_состояние#имя_перехода#новое_состояние.
Состояние | Сигнал | Расшифровка сигнала | Ключ | Состояние | Переход |
0 | nr | Имя считывателя | 0_nr | 1 | 0#1 |
0 | nr | Имя карты | 0_nc | 2 | 0#2 |
1 | nc | Имя карты | 1_nc | 0 | 1#0#0 |
1 | er | Ошибка | 1_er | 0 | 1#1#0 |
2 | nr | Имя считывателя | 2_nr | 0 | 2#0#0 |
2 | er | Ошибка | 2_er | 0 | 2#1#0 |
Для того, чтобы можно было использовать алгоритм, приведенный выше, изменим правило образования имени состояния в gen[1]: имя_перехода#имя_нового_состояния. Тогда вектор gen, определяющий поведение машины будет иметь вид:
gen=[[0_nr, 0_nc, 1_nc, 1_er, 2_nr, 2_er], [1, 2, 0#0, 1#0, 0#0, 1#0]]
Минимальные изменения алгоритма связаны с определением нового состояния, т.к. nState=gen[1][keyInd] содержит не имя нового состояния, а его комбинацию с именем перехода, но совершенно очевидно, как его найти.
Машина в режиме регистрации на переходах выполняет другие действия, она не общается с турникетом
Переход | Действия |
0#1 | Определение имени считывателя в системе |
0#2 | Определение имени карты в системе |
1#0#0, 2#0#0 | Запись новых данных |
1#1#0, 2#1#0 | Сообщение об ошибке |
Машина состояний турникета
Турникет представляет собой «сложное» устройство, в котором есть два замка и устройство фиксирующее переход, обычно это геркон. Есть еще сигнальные лампы, показывающие состояние замков и возможно, источник звука. Один замок назовем входом, а другой — выходом. Так как каждый замок может находиться в одном из двух состояний (открыт/закрыт), то у турникета могут быть следующие состояния:
Управление турникетом осуществляется по командам считывателя, командам управляющего устройства (в нашем случае — тачскрином планшета), а также сигналу геркона. Кроме того, для того, чтобы предотвратить «зависание» системы в случае отказа от перехода (считыватель сработал, замок открылся, а посетитель не прошел), в систему добавлен таймер, который также влияет на переходы в машине турникета.
Переход в эти состояния осуществляются при получении одного из сигналов: открыть вход, открыть выход (от считывателя), закрыть вход/выход (от геркона — турникета), открыть/закрыть вход/выход (от тачскрина), закрыть вход/выход (от таймера):
Состояние | Сигнал | Расшифровка сигнала | Ключ | Состояние | Переход |
0 | eo | Открыть вход (считыватель) | 0_eo | 1 | 0#0#1 |
0 | xo | Открыть выход (считыватель) | 0_xo | 2 | 0#0#2 |
0 | ep | Открыть вход (тачскрин) | 0_ep | 1 | 0#1#1 |
0 | xp | Открыть выход (тачскрин) | 0_xp | 2 | 0#1#2 |
1 | gt | Закрыть вход (геркон) | 1_gt | 0 | 1#0#0 |
1 | tt | Закрыть вход (таймер) | 1_tt | 0 | 1#1#0 |
2 | gt | Закрыть выход (геркон) | 2_gt | 0 | 2#0#0 |
2 | tt | Закрыть выход (таймер) | 2_tt | 0 | 2#1#0 |
Машина состояний турникета с сигналами и переходами, приведенными в таблице, будет иметь вид:
Машина турникета выполняет следующие действия на переходах:
Переход | Действия |
0#0#1, 0#1#1 | Открытие входа, включение таймера, вызов машины интерфейса(сигнал eo) |
0#0#2, 0#1#2 | Открытие выхода, включение таймера, вызов машины интерфейса(сигнал eo) |
1#0#0 | Закрытие входа, запись данных в связи, вызов машины считывателя (сигнал ts), вызов машины интерфейса (сигнал ts) |
1#1#0 | Закрытие входа, вызов машины считывателя (сигнал ts), вызов машины интерфейса (сигнал ts) |
2#0#0 | Закрытие выхода, запись данных в связи, вызов машины считывателя (сигнал ts), вызов машины интерфейса (сигнал ts) |
2#1#0 | Закрытие выхода, вызов машины считывателя (сигнал ts), вызов машины интерфейса (сигнал ts) |
Построенная машина турникета позволяет осуществить односторонний проход в любом направлении при регистрации карты со статусом постоянная или временная на считывателе турникета и выход посетителя с картой со статусом разовая только через ее регистрацию на считывателе картоприемника. Также возможно управление турникетом с планшета (нажатие на стрелку 1 откроет вход, а 2 — выход. Закрытие происходит по сигналам геркона и таймера):
В тоже время, периодически возникают случаи, когда необходимо открытие или закрытие входа/выхода по кнопке безотносительно к наличию карты. Для этого используются «светофоры» слева (вход) и справа (выход). Карты на входе или выходе работают только тогда, когда у соответствующего светофора «горит» желтый свет. Красный сигнал закрывает соответствующий замок и никакой картой его открыть нельзя, а зеленый — наоборот открывает и ни геркон, ни таймер его закрыть не могут.
И теперь возникает вопрос: если при нажатии на зеленую кнопку светофора мы открываем вход, т.е. осуществляем в машине турникета переход в состояние 1, то как предотвратить переход в состояние 0 по сигналу геркона gt или таймера tt? Понятно, что при «машинном» подходе не хочется рассматривать работу с флагами и т.п., а хочется работать с машиной, заданной вектором gen.
Расширим понятие ключа в векторе gen. Добавим в строку для формирование ключа величину, которую будем называть условием, т.е ключ это состояние_сигнал+условие. Определим следующие значения условия в зависимости, какой свет «горит» на светофорах и какой ключ будет для сигналов от геркона gt и таймера tt в состоянии 1:
Светофор | Цвет светофора | Условие | Ключ |
Оба светофора | Желтый | 1_gt, 1_tt | |
Только вход | Не желтый (красный или зеленый) | ls | 1_gtIs, 1_ttIs |
Только выход | Не желтый (красный или зеленый) | rs | 1_gtrs, 1_ttrs |
Оба светофора | Не желтый (красный или зеленый) | bs | 1_gtbs, 1_ttbs |
Теперь мы знаем ответ на вопрос. После открытия входа зеленой кнопкой левого светофора сигнал от геркона создаст ключ 1_gtIs, а сигнал от таймера — 1_ttIs, которых нет в векторе gen и поэтому никакого перехода не произойдет. Турникет останется в состоянии 1.
Рассмотрим дополнительные переходы в машине турникета связанные с нажатиями на кнопки светофоров. Сигналы от светофора входа обозначим lr — красный, ly- желтый, lg — зеленый, а от светофора выхода — rr — красный, ry- желтый, rg — зеленый.
Состояние | Сигнал | Расшифровка сигнала | Ключ | Состояние | Переход |
0 | lg | Открыть вход зеленой кнопкой светофора | 0_lg, 0_lgls, 0_lgrs,0_lgbs | 1 | 0#2#1 |
1 | lr,ly | Закрыть вход красной или желтой кнопкой светофора | 1_lrls, 1_lrbs, 1_lyls, 1_lybs |
0 | 1#2#0 |
0 | rg | Открыть выход зеленой кнопкой светофора | 0_rg, 0_rgls, 0_rgrs,0_rgbs | 2 | 0#2#2 |
2 | ry,rr | Закрыть выход красной или желтой кнопкой светофора | 2_ryrs,2_rrrs, 2_ryrs,2_rrbs | 0 | 2#2#0 |
1 | rg | Открыть выход зеленой кнопкой светофора (при открытом входе) | 1_rgls,1_rgbs | 3 | 1#2#3 |
2 | lg | Открыть вход зеленой кнопкой светофора (при открытом выходе) | 2_lgrs,2_lgbs | 3 | 2#2#3 |
3 | lr,ly | Закрыть вход красной или желтой кнопкой светофора | 3_lybs,3_lrbs | 1 | 3#2#1 |
3 | ry,rr | Закрыть выход красной или желтой кнопкой светофора | 3_rybs,3_rrbs | 2 | 3#2#2 |
Соответствующие переходы в машине состояний:
Полный вектор gen для машины состояний турникета:
gen=[[0_eo, 0_xo, 0_ep, 0_xp, 1_gt, 1_tt, 2_gt, 2_tt, 0_lg, 0_lgls, 0_lgrs, 0_lgbs, 1_lrls, 1_lrbs, 1_lyls, 1_lybs,
0_rg, 0_rgls, 0_rgrs, 0_rgbs, 2_ryrs, 2_rrrs, 2_ryrs, 2_rrbs, 1_rgls, 1_rgbs, 2_lgrs, 2_lgbs,
3_lybs, 3_lrbs, 3_rybs, 3_rrbs, 1_xols, 1_xpls, 3_gtls, 3_ttls, 2_eors, 2_eprs, 3_gtrs, 3_ttrs],
[0#1, 0#2, 1#1, 1#2, 0#0,1#0, 0#0, 1#0, 2#1, 2#1, 2#1, 2#1, 2#0, 2#0, 2#0, 2#0,
2#2, 2#2, 2#2, 2#2, 2#0, 2#0, 2#0, 2#0, 2#3, 2#3, 2#3, 2#3,
2#1, 2#1, 2#2, 2#2, 0#3, 1#3, 0#1, 1#1, 0#3, 1#3, 0#2, 1#2]].
Действия на дополнительных переходах понятны из расшифровок сигнала.
Машина состояний интерфейса
Управление турникетов может осуществляться с планшета и наоборот, состояние интерфейса зависит от сигналов от считывателя и турникета.
Как видно из начального состояния интерфейса (рисунок выше) для управления используется две кнопки в виде стрелок и по три кнопки на каждом светофоре. Стрелки работают только тогда, когда на соответствующем светофоре желтый свет. Если на светофоре красный или зеленый, то стрелка не работает. Другими словами, у светофора есть состояние включен и выключен. Также по два таких же состояния есть и у стрелок.
В итоге получаем следующие возможные состояния интерфейса:
- все выключено. Ожидаем нажатие на кнопку;
- включена стрелка-вход;
- включена стрелка-выход;
- включен светофор-вход;
- включен светофор-выход;
- включены оба светофора;
- включена стрелка-выход при включенном светофоре-вход;
- включена стрелка-вход при включенном светофоре-выход.
Соберем, как и ранее все сигналы и переходы в таблицу (укажем сигналы, относящиеся только к левой половине диаграммы, а вектор gen приведем полностью).
Состояние | Сигнал | Расшифровка сигнала | Ключ | Состояние | Переход |
0 | ae | Нажать на стрелку-вход | 0_ae | 1 | 0#0#1 |
0 | eo | Открыть вход (считыватель) | 0_eo | 1 | 0#1#1 |
1 | ts | Закрыть вход (турникет) | 1_ts | 0 | 1#0 |
0 | lr | Нажать красный сигнал светофора-вход | 0_lr | 3 | 0#0#3 |
0 | lg | Нажать зеленый сигнал светофора-вход | 0_lg | 3 | 0#1#3 |
3 | lr | Нажать красный сигнал светофора-вход | 3_lr | 3 | 3#0#3 |
3 | lg | Нажать зеленый сигнал светофора-вход | 3_lg | 3 | 3#1#3 |
3 | ly | Нажать желтый сигнал светофора-вход | 3_ly | 0 | 3#0 |
3 | rr | Нажать красный сигнал светофора-выход | 3_rr | 5 | 3#0#5 |
3 | rg | Нажать зеленый сигнал светофора-выход | 3_rg | 5 | 3#1#5 |
3 | ax | Нажать на стрелку-выход | 3_ax | 6 | 3#0#6 |
3 | xo | Открыть выход (считыватель) | 3_xo | 6 | 3#1#6 |
5 | ry | Нажать желтый сигнал светофора-выход | 5_ry | 3 | 5#3 |
6 | ts | Закрыть вход (турникет) | 6_ts | 3 | 6#3 |
Соответствующие переходы в машине:
Полный вектор gen для машины состояний интерфейса:
gen=[[0_ae, 0_eo, 0_ax, 0_ex, 1_ts, 2_ts, 0_lr, 0_lg, 0_rr, 0_rg, 3_ly, 4_ry, 3_ax, 3_xo, 6_ts,
4_ae, 4_eo, 7_ts, 3_lr, 3_lg, 3_rr, 3_rg, 4_rr, 4_rg, 4_lr, 4_lg, 5_ry, 5_ly, 5_lr, 5_lg, 5_rr, 5_rg],
[0#1, 1#1, 0#2, 1#2, 0, 0, 0#3, 1#3, 0#4, 1#4, 0, 0, 0#6, 1#6, 3,
0#7, 1#7, 4, 0#3, 1#3, 0#5, 1#5, 0#4, 1#4, 0#5, 1#5, 3, 4, 0#5, 1#5, 2#5, 3#5]]
Действия на переходах иллюстрируются состояниями интерфейса.
Кроме того, на переходах изменяется условие для машины турникета и происходит ее вызов (сигналы ep,xp,lr,lg,ly,rr,rg,ry):
Переход | Условие |
0#0#3,0#1#3 | ls |
3#0 | |
3#0#5,3#1#5 | bs |
5#3 | ls |
0#0#4,0#1#4 | rs |
4#0 | |
4#0#5,4#1#5 | bs |
5#4 | rs |
Таким образом, мы построили при помощи трех машин состояний, синхронизирующихся при помощи обменов сигналами, простую динамическую модель СКУД, позволяющую реализовывать достаточно сложную систему управления.
В дальнейшем будет приведен живой пример реализации СКУД, основанной на принципах изложенных в этой и предыдущей статьях.
Поделиться с друзьями
Lugard
Фраза «Кроме того, на переходах изменяется условие для машины турникета и происходит ее вызов (сигналы ep,xp,lr,lg,ly,rr,rg,ry):» предполагает, что машина турникета получит сигналы от машины интерфейса, но при этом машина турникета посылает сигналы другим машинам, в том числе и машине интерфейса для реагирования на внешнее воздействие. Как Вы добиваетесь отсутствия зацикленности в системе?
LRpro
Вызов машины турникета со стороны машины интерфейса, например, «открыть вход» происходит на переходе 0#0#1. Машина интерфейса переходит в состояние 1, из которого может выйти только по сигналу ts от машины турникета. При получении такового она возвращается в исходное состояние по переходу 0#1. Из-за различных переходов и моментов времени зацикленность не возникает, а возникает общение машин (вопрос-ответ).
Lugard
Различные сигналы не могут избавить от циклов, если одна машина сразу посылает сигналы из кода, не ожидая «реальных» сигналов от устройств и это может приводить к дублированию данных по той причине, что даже если машины и не перешли в бесконечный цикл, то все равно могут сработать несколько раз пока условия будут выполняться. По описанию машин я понял, что у Вас такие ситуации — генерация сигнала по событию из кода, а не от устройства — присутствуют в коде системы. Или я ошибаюсь?
LRpro
Если считать сигналы от таймеров сигналами «из кода», то кроме них в системе других сигналов «из кода» нет. В машине нет условий для «пока условия будут выполняться».