def get_automaton(self, chat_id): """ Получает конечный автомат для конкретного пользователя Находим в словаре (в режиме POLLING) или загружаем из pickle (в режиме WEBHOOK) автомат по ID пользователя Если сохраненного автомата нет, создаем его и помещаем в хранилище """ if self.mode == BotMode.POLLING: if chat_id in self.chats: automaton = self.chats[chat_id] else: automaton = FSA(chat_id, self.command_tree, self.bot, self.logger) self.chats[chat_id] = automaton else: assert self.fsa_serializer != None, "Property 'fsa_serializer' must be set in 'webhook' mode" automaton = FSA(chat_id, self.command_tree, self.bot, self.logger) automaton_loaded = self.fsa_serializer.load_fsa(chat_id) if automaton_loaded: filtered_fields = { key: value for key, value in automaton_loaded.__dict__.items() if key not in FSA.unstored_fields } automaton.__dict__.update(filtered_fields) return automaton
def generate_transactions(version): fsas = [] insert_fn = insert_v1 if int(version) == 1 else insert_v2 engine = create_engine(config["db_connect"]) conn = engine.connect() for idx in range(config['fsa1_count']): fsas.append(FSA(idx, lambda x: insert_fn(x, conn), 1, config['fsa1'])) for idx in range(config['fsa2_count']): fsas.append(FSA(config['fsa1_count'] + idx, lambda x: insert_fn(x, conn), 1, config['fsa2'])) idx = config['fsa1_count'] + config['fsa2_count'] while len(fsas) > 0: fsa = random.choice(fsas) fsa.step() if fsa.done(): log.debug(f"FSA({fsa.fsa_id}) done") fsas.remove(fsa) if random.uniform(0, 1) < config['fsa1_birthrate']: log.debug("new fsa1") fsas.append(FSA(idx, lambda x: insert_fn(x, conn), 1, config['fsa1'])) idx += 1 if random.uniform(0, 1) < config['fsa2_birthrate']: log.debug("new fsa2") fsas.append(FSA(idx, lambda x: insert_fn(x, conn), 2, config['fsa2'])) idx += 1 log.debug(f"counts {np.unique([f.fsa_type for f in fsas], return_counts=True)}")
def parse_table(name, table, subsets): lines = table.split('\n') if len(lines) < 4: raise ValueError,\ "Rule %s has too few lines to be an FSA table." % name pairs1 = lines[1].strip().split() pairs2 = lines[2].strip().split() if len(pairs1) != len(pairs2): raise ValueError,\ "Rule %s has pair definitions that don't line up." % name pairs = [KimmoPair(p1, p2) for p1, p2 in zip(pairs1, pairs2)] finals = [] fsa = FSA() for line in lines[3:]: line = line.strip() if not line: continue groups = re.match(r'(\w+)(\.|:)\s*(.*)', line) if groups is None: raise ValueError,\ "Can't parse this line of the state table for rule %s:\n%s"\ % (name, line) state, char, morestates = groups.groups() if fsa.start() == 0: fsa.set_start(state) if char == ':': finals.append(state) fsa.add_state(state) morestates = morestates.split() if len(morestates) != len(pairs): raise ValueError,\ "Rule %s has a row of the wrong length:\n%s\ngot %d items, should be %d"\ % (name, line, len(morestates), len(pairs)) for pair, nextstate in zip(pairs, morestates): fsa.insert_safe(state, pair, nextstate) fsa.set_final(finals) return KimmoFSARule(name, fsa, subsets)
def from_dfa_dict(name, states, subsets): fsa = FSA() pairs = set([KimmoPair.make('@')]) for (statename, trans) in states.items(): for label in trans: if label != 'others': pairs.add(KimmoPair.make(label)) for (statename, trans) in states.items(): parts = statename.split() source = parts[-1] if not parts[0].startswith('rej'): fsa.add_final(source) if fsa.start() == 0 and source in ['begin', 'Begin', '1', 1]: fsa.set_start(source) if source in ['start', 'Start']: fsa.set_start(source) used_pairs = set() for label in trans: if label != 'others': used_pairs.add(KimmoPair.make(label)) for label, target in trans.items(): if label.lower() == 'others': fsa.insert_safe(source, KimmoPair.make('@'), target) for pair in pairs.difference(used_pairs): fsa.insert_safe(source, pair, target) else: fsa.insert_safe(source, KimmoPair.make(label), target) return KimmoFSARule(name, fsa, subsets)
def fsa_test(test_string): # Defining FSA which accepts strings with even number of a's and b's fsa_states = ["q0", "q1", "q2", "q3"] fsa_alph = ["a", "b"] fsa_start = "q0" fsa_final = ["q0"] fsa_trans = { "q0": { "a": "q2", "b": "q1" }, "q1": { "a": "q3", "b": "q0" }, "q2": { "a": "q0", "b": "q3" }, "q3": { "a": "q1", "b": "q2" }, } test_fsa = FSA(fsa_states, fsa_alph, fsa_final, fsa_start, fsa_trans) if (test_fsa.accept_string(test_string)): print "Yay! this FSA does accept the string : " + test_string else: print "NO! this FSA doesnt accept the string : " + test_string
def from_text(text): fsa = FSA([], {}, 'Begin', ['End']) state = 'Begin' for line in text.split('\n'): line = line.strip() if not line or line.startswith(';'): continue if line[-1] == ':': state = line[:-1] else: if line.split()[0].endswith(':'): parts = line.split() name = parts[0][:-1] next_states = parts[1:] for next in next_states: fsa.insert_safe(name, None, next) elif len(line.split()) > 2: # this is a lexicon entry word, next, features = line.split(None, 2) if word.startswith('"') or\ word.startswith("'") and word.endswith("'"): word = eval(word) if features: if features == 'None': features = None elif features[0] in '\'"{': features = YAMLwrapper(features) fsa.insert_safe(state, (word, features), next) elif len(line.split()) == 2: word, next = line.split() features = '' if word == "''": word = '' fsa.insert_safe(state, (word, features), next) else: print "Ignoring line in morphology: %r" % line return KimmoMorphology(fsa)
def _parse_context(self, tokens, i, reverse): (j, tree) = self._parse_list(tokens, i) if j == i: return (i, None) sigma = set() self._collect_alphabet(tree, sigma) fsa = FSA(sigma) final_state = self._build_fsa(fsa, fsa.start(), tree, reverse) fsa.set_final([final_state]) #fsa.pp() dfa = fsa.dfa() #dfa.pp() dfa.prune() #dfa.pp() return (j, dfa)
def setUp(self): self.fsa = FSA()