def concatenate_nfa(self): nfa_last = self.nfa_stack.pop() nfa_first = self.nfa_stack.pop() nfa_first.end.accept = False nfa_first.end.epsilon.append(nfa_last.start) nfa = NFA(nfa_first.start, nfa_last.end) self.nfa_stack.append(nfa)
def char_nfa(self, token): start_status = Status() end_status = Status() start_status.translate(token.value, end_status) end_status.accept = True nfa = NFA(start_status, end_status) self.nfa_stack.append(nfa)
def plus_nfa(self): start_status = Status() end_status = Status() end_status.accept = True nfa = self.nfa_stack.pop() nfa.end.accept = False nfa.end.epsilon.append(nfa.start) start_status.epsilon.append(nfa.start) nfa.end.epsilon.append(end_status) self.nfa_stack.append(NFA(start_status, end_status))
def bar_nfa(self): nfa_last = self.nfa_stack.pop() nfa_first = self.nfa_stack.pop() start_status = Status() end_status = Status() end_status.accept = True start_status.epsilon.append(nfa_first.start) start_status.epsilon.append(nfa_last.start) nfa_first.end.epsilon.append(end_status) nfa_last.end.epsilon.append(end_status) nfa_first.end.accept = False nfa_last.end.accept = False nfa = NFA(start_status, end_status) self.nfa_stack.append(nfa)
def reverse(self): # reset Status count Status.count = 0 end_status = Status() end_status.accept = True accept_status_list = [] status_list = {self.dfa.start: end_status} work_list = [self.dfa.start] while work_list: status = work_list.pop() new_status = status_list[status] if status not in self.dfa.table: # this status gos no where continue for k, v in self.dfa.table[status].items(): sub_status = None if v not in status_list: sub_status = Status() if v.accept: accept_status_list.append(sub_status) status_list.update({v: sub_status}) work_list.append(v) else: sub_status = status_list[v] sub_status.translate(k, new_status) start_status = Status() start_status.epsilon = accept_status_list return NFA(start_status, end_status)