1

例如,我正在使用Pytransitions,并且我有一些状态机

from transitions import Machine
from transitions import EventData


class Matter(object):
    def __init__(self):
        transitions = [
            {'trigger': 'heat', 'source': 'solid', 'dest': 'liquid'},
            {'trigger': 'heat', 'source': 'liquid', 'dest': 'gas'},
            {'trigger': 'cool', 'source': 'gas', 'dest': 'liquid'},
            {'trigger': 'cool', 'source': 'liquid', 'dest': 'solid'}
        ]
        self.machine = Machine(
                model=self,
                states=['solid', 'liquid', 'gas'],
                transitions=transitions,
                initial='solid',
                send_event=True
        )

    def on_enter_gas(self, event: EventData):
        print(f"entering gas from {event.transition.source}")

    def on_enter_liquid(self, event: EventData):
        print(f"entering liquid from {event.transition.source}")

    def on_enter_solid(self, event: EventData):
        print(f"entering solid from {event.transition.source}")

是否有一些图书馆支持的方式来跟踪所有州的历史?

我现在手动做的是初始化:

after_state_change=lambda event: self._on_after_state_change(event)

def _on_after_state_change(self, event: EventData):
    to_state = event.transition.dest
    self._history_df.append({
        "start_index": self._index,
        "state": to_state
    }, ignore_index=True)

我想知道该库是否支持一些可查询的日志记录,这意味着不仅将事件转储到文件中,而且还能够将它们保存在列表中。

4

1 回答 1

1

Transitions 没有内置的历史记录。如果您只想跟踪以前的状态,这个GitHub 问题可能会有所帮助:

由于具有转换的有状态对象是模型,因此您可以使用 state 属性来跟踪状态更改:

from transitions import Machine
import collections


# if you like your machine to act as a model, let Model inherit from Machine
class Model(object):

    def __init__(self, history_length):
        self.state_history = collections.deque(maxlen=history_length)

    @property
    def state(self):
        return self.state_history[-1]

    @state.setter
    def state(self, value):
        self.state_history.append(value)


model = Model(3)
machine = Machine(model, states=['A', 'B', 'C', 'D'], initial='A')
print(model.state)  # >>> A

model.to_B()
model.to_C()
model.to_A()
model.to_D()

print("->".join(model.state_history))  # >>> C->A->D

这仅适用于model_attribute='state'(默认值)。如果您更改了“有状态”模型字段的名称,则需要相应地调整上述属性。

如果您对 all 感兴趣,那么EventData您的方法似乎是解决方案。不过,您可以省略 lambda。after_state_change=self._on_after_state_changeafter_state_change='_on_after_state_change'(如果该方法是模型的一部分)就足够了。

上面提到的dequeue(或queue.Queue)是“可查询的”,您可以使用过滤器或列表推导。如果您需要更复杂的东西,pandas(考虑到您的历史名称,您可能已经使用过)或sqlite可能更合适。

于 2021-08-02T12:08:18.760 回答