簡要回顧上一篇文章簡易版訂單系統定義的幾個初始狀態java
秉着不重複造輪子的原則,筆者以前訂單系統主要借鑑了hadoop yarn狀態機的設計,並進行了一點小小的優化和封裝編程
yarn狀態機多弧過渡部分由於沒有用到直接省略(感興趣的同窗能夠本身去查看源碼,筆者認爲多弧過渡主要是次態的可選擇性,可是反而增長了不肯定性因此沒有采用)接下來的部分主要是源碼解析網絡
狀態機主要類圖以下app
hadoop底層代碼oop
//此方法在addTransition方法中調用 主要是構建鏈表
private StateMachineFactory (StateMachineFactory<OPERAND, STATE, EVENTTYPE, EVENT> that, ApplicableTransition<OPERAND, STATE, EVENTTYPE, EVENT> t) {
this.defaultInitialState = that.defaultInitialState;
this.transitionsListNode
= new TransitionsListNode(t, that.transitionsListNode);
this.optimized = false;
this.stateMachineTable = null;
}
//installTopology 中調用進行初始化過程 主要邏輯封裝在makeStateMachineTable()方法中
private StateMachineFactory (StateMachineFactory<OPERAND, STATE, EVENTTYPE, EVENT> that, boolean optimized) {
this.defaultInitialState = that.defaultInitialState;
this.transitionsListNode = that.transitionsListNode;
this.optimized = optimized;
if (optimized) {
makeStateMachineTable();
} else {
stateMachineTable = null;
}
}
//
private void makeStateMachineTable() {
//建立堆棧 ApplicableTransition將此前鏈表的各個ApplicableTransition壓入棧中
Stack<ApplicableTransition<OPERAND, STATE, EVENTTYPE, EVENT>> stack =
new Stack<ApplicableTransition<OPERAND, STATE, EVENTTYPE, EVENT>>();
Map<STATE, Map<EVENTTYPE, Transition<OPERAND, STATE, EVENTTYPE, EVENT>>>
prototype = new HashMap<STATE, Map<EVENTTYPE, Transition<OPERAND, STATE, EVENTTYPE, EVENT>>>();
prototype.put(defaultInitialState, null);//默認狀態
// 構建拓撲表 每一個狀態都有一個對應的
stateMachineTable
= new EnumMap<STATE, Map<EVENTTYPE,
Transition<OPERAND, STATE, EVENTTYPE, EVENT>>>(prototype);
for (TransitionsListNode cursor = transitionsListNode;
cursor != null;
cursor = cursor.next) {
stack.push(cursor.transition);
}
//apply方法就是完整構建拓撲表過程 此處簡要描述 在拓撲表中找到當前訂單狀態的動做映射map,而後把動做放入此map中
while (!stack.isEmpty()) {
stack.pop().apply(this);
}
}
複製代碼
//建立一個初始狀態機
private static final StateMachineFactory<OrderRequest, OrderStatusEnum, OrderEvent.OrderEventEnum, OrderEvent> stateMachineFactory = new StateMachineFactory<OrderRequest, OrderStatusEnum, OrderEvent.OrderEventEnum, OrderEvent>(OrderStatusEnum.INVALID)
//調用私有構造方法 添加單弧事件去transitionsListNode
.addTransition(OrderStatusEnum.INVALID, OrderStatusEnum.SUBMIT_ORDER, OrderEvent.OrderEventEnum.INIT_SUCCESS, new OrderInitTransition())
//構建拓撲表
.installTopology();
複製代碼
//將自定義request參數傳入狀態機,根據傳入status爲默認狀態返回一個狀態機。
//若是拓撲表爲構建會從新執行一遍構建過程
orderStateMachine = OrderStateMachine.getStateMachine(request, OrderStatusEnum.getById(request.getOrderStatus()));
//狀態轉移過程 返回次態
orderStateMachine.doTransition(orderEvent.getOrderEvent(), orderEvent)
//具體doTranstion方法
private STATE doTransition (OPERAND operand, STATE oldState, EVENTTYPE eventType, EVENT event) throws InvalidStateTransitionException {
//根據訂單狀態找到以前構建的map
Map<EVENTTYPE, Transition<OPERAND, STATE, EVENTTYPE, EVENT>> transitionMap
= stateMachineTable.get(oldState);
if (transitionMap != null) {
//根據事件找到具體動做
Transition<OPERAND, STATE, EVENTTYPE, EVENT> transition
= transitionMap.get(eventType);
if (transition != null) {
//執行動做
return transition.doTransition(operand, oldState, event, eventType);
}
}
throw new InvalidStateTransitionException(oldState, eventType);
}
複製代碼