Esempio n. 1
0
 def test_concat(self):
     alphabet = [0, 1]
     s = ["A", "B"]
     # lang: 0, 01, 011, 0111, ... = 01*
     transitions = [("A", 0, "B"), ("B", 1, "B")]
     acc_s = ["B"]
     rej_s = ["A"]
     dfa1 = DFA.build(alphabet=alphabet, states=s, start_state="A",
                      accept_states=acc_s, reject_states=rej_s,
                      transitions=transitions)
     s = ["X", "Y", "Z"]
     transitions = [("X", 0, "Y"), ("Y", 1, "Z"), ("Z", 1, "Z")]
     acc_s = ["Y", "Z"]
     rej_s = ["X"]
     dfa2 = DFA.build(alphabet=alphabet, states=s, start_state="X",
                      accept_states=acc_s, reject_states=rej_s,
                      transitions=transitions)
     dfa3 = (dfa1 * dfa2).minimize().rename()
     # dfa3 is 01*01*,
     self.assertEqual(dfa3.membership([1]), Result.reject)
     self.assertEqual(dfa3.membership([0, 0]), Result.accept)
     self.assertEqual(dfa3.membership([0, 1, 0]), Result.accept)
     self.assertEqual(dfa3.membership([0, 0, 0]), Result.reject)
     self.assertEqual(dfa3.membership([0, 1, 1]), Result.reject)
     self.assertEqual(dfa3.membership([0, 1, 1, 1, 1, 1]), Result.reject)
Esempio n. 2
0
 def test_union_intersection_subset(self):
     alphabet = [0, 1]
     s = ["A", "B"]
     transitions = [("A", 0, "A"), ("A", 1, "B"),
                    ("B", 0, "A"), ("B", 1, "A")]
     acc_s = ["B"]
     rej_s = ["A"]
     dfa1 = DFA.build(alphabet=alphabet, states=s, start_state="A",
                      accept_states=acc_s, reject_states=rej_s,
                      transitions=transitions)
     s = ["C", "D"]
     transitions = [("C", 0, "D"), ("C", 1, "C"),
                    ("D", 0, "D"), ("D", 1, "C")]
     acc_s = ["C"]
     rej_s = ["D"]
     dfa2 = DFA.build(alphabet=alphabet, states=s, start_state="D",
                      accept_states=acc_s, reject_states=rej_s,
                      transitions=transitions)
     udfa = dfa1 | dfa2
     idfa = dfa1 & dfa2
     self.assertEqual(idfa.membership([0, 1]), Result.accept)
     self.assertEqual(idfa.membership([1]), Result.accept)
     self.assertEqual(dfa1.membership([0, 1, 1]), Result.reject)
     self.assertEqual(udfa.membership([0, 1, 1]), Result.accept)
     self.assertTrue(dfa1.issubset(dfa2))
Esempio n. 3
0
def build_PTA(dataset):
    # based on:
    # de la Higuera: Grammatical Inference (2010), p.  239, Algorithm 12.1
    labels_available = isinstance(dataset, AnnotatedDataset)
    name_generator = state_generator()
    start = next(name_generator)
    states = { start }
    alp = dataset.alphabet
    accept = set()
    reject = set()
    tr = collections.defaultdict(lambda: None)
    for sample in dataset:
        curr_state = start
        for symbol in sample[0]:
            next_state = tr.get((curr_state, symbol), None)
            if next_state is None:
                next_state = next(name_generator)
                states.add(next_state)
                tr[curr_state, symbol] = next_state
            curr_state = next_state
        if labels_available:
            if sample[1]:
                accept.add(curr_state)
            else:
                reject.add(curr_state)
        else:
            accept.add(curr_state)
    # delta = lambda s, a: tr.get((s, a), None)
    delta = lambda q, a: tr[q, a]
    return DFA(alp, states, start, accept, reject, delta, tr)
Esempio n. 4
0
    def build_DFA(self):
        # observation table must be closed and complete!
        state_map = dict()
        name_gen = state_generator()
        for v in sorted(self.red_set, key=len):
            unique = True
            for r in sorted(state_map.keys(), key=len):
                # check if there exists a compatible red state
                # in gold algorithm, this can never happen
                # but in lstar it can
                if self.states_compatible(r, v):
                    unique = False
                    state_map[v] = state_map[r]
            if unique:
                state_map[v] = next(name_gen)
        states = set(state_map.values())
        accept = set()
        reject = set()
        start = state_map[tuple()]
        tr = collections.defaultdict(lambda: None)
        for r in self.red_set:
            if self(r, tuple()) == 1:
                accept.add(state_map[r])
            else:
                reject.add(state_map[r])

        for q in self.red_set:
            for sym in self.alphabet:
                for u in self.red_set:
                    if self.states_compatible(u, q + (sym, )):
                        tr[state_map[q], sym] = state_map[u]
        # print states, accept_states, reject_states
        delta = lambda q, a: tr[q, a]
        return DFA(set(self.alphabet), states, start, accept, reject, delta)
Esempio n. 5
0
 def test_minimize(self):
     a = "a"
     b = "b"
     alphabet = [a, b]
     s = [0, 1, 2, 3, 4, 5, 6]
     transitions = [(0, a, 0), (0, b, 0),
                    (1, a, 2), (1, b, 5),
                    (2, a, 3), (2, b, 0),
                    (3, a, 3), (3, b, 4),
                    (4, a, 3), (4, b, 0),
                    (5, a, 6), (5, b, 0),
                    (6, a, 0), (6, b, 5)]
     acc_s = [0, 5]
     rej_s = [1, 2, 4, 6]
     dfa = DFA.build(alphabet=alphabet, states=s, start_state=1,
                      accept_states=acc_s, reject_states=rej_s,
                      transitions=transitions)
     mindfa = dfa.minimize()
     # quick'n'dirty test whether automaton is equivalent
     brzozowski = nfa.NFA.viewDFA(dfa).reverse().determinize()
     brzozowski = nfa.NFA.viewDFA(brzozowski).reverse().determinize()
     self.assertTrue(mindfa == dfa)
     self.assertTrue(brzozowski == mindfa)
     self.assertEqual(mindfa.membership("ab"), Result.accept)
     self.assertEqual(mindfa.membership("bb"), Result.accept)
     self.assertEqual(mindfa.membership("baa"), Result.accept)
     self.assertEqual(mindfa.membership("aabb"), Result.accept)
     self.assertEqual(mindfa.membership("aaaaaaaaaabbbbb"), Result.accept)
Esempio n. 6
0
 def test_incomplete(self):
     alphabet = ["a", "b"]
     s = [1, 2, 3, 4]
     transitions = [(1, "b", 1), (1, "a", 2),
                    (2, "a", 3), (2, "b", 4)]
     acc_s = [2, 3]
     rej_s = [4]
     dfa = DFA.build(alphabet=alphabet, states=s, start_state=1,
                     accept_states=acc_s, reject_states=rej_s,
                     transitions=transitions)
     self.assertFalse(dfa.is_complete())
     dfa.transitions = None
     dfa.complete(sink=4)
     self.assertTrue(dfa.is_complete())
Esempio n. 7
0
 def setUp(self):
     alphabet = ["a", "b"]
     s = ["q1", "q2", "q3", "q4"]
     transitions = [("q1", "b", "q1"), ("q1", "a", "q2"),
                    ("q2", "a", "q3"), ("q2", "b", "q4"),
                    ("q3", "a", "q4"), ("q3", "b", "q3"),
                    ("q4", "a", "q2"), ("q4", "b", "q1")]
     acc_s = ["q2", "q3"]
     rej_s = ["q4"]
     self.fsa = DFA.build(alphabet=alphabet, states=s,
                          start_state="q1",
                          accept_states=acc_s,
                          reject_states=rej_s,
                          transitions=transitions)
Esempio n. 8
0
    def test_equality(self):
        alphabet = [0, 1]
        s = ["A", "B"]
        # lang: 0, 01, 011, 0111, ... = 01*
        transitions = [("A", 0, "B"), ("B", 1, "B")]
        acc_s = ["B"]
        rej_s = ["A"]
        dfa1 = DFA.build(alphabet=alphabet, states=s, start_state="A",
                         accept_states=acc_s, reject_states=rej_s,
                         transitions=transitions)
        s = ["X", "Y", "Z"]
        transitions = [("X", 0, "Y"), ("Y", 1, "Z"), ("Z", 1, "Z")]
        acc_s = ["Y", "Z"]
        rej_s = ["X"]
        dfa2 = DFA.build(alphabet=alphabet, states=s, start_state="X",
                         accept_states=acc_s, reject_states=rej_s,
                         transitions=transitions)

        # test incompleteness
        self.assertEqual(dfa1.membership([1, 1, 1]), Result.reject)

        dfa1.complete()
        dfa2.complete()
        self.assertTrue(dfa1 == dfa2)
        
        # test equivalence pairs
        eq_pairs = {('A', 'X'), ('B', 'Y'), ('B', 'Z'), (-1, -1)}
        self.assertEqual(dfa1.equivalent_states(dfa2), eq_pairs)
        
        udfa = dfa1 | dfa2
        self.assertEqual(udfa.membership([0]), Result.accept)
        self.assertEqual(udfa.membership([1]), Result.reject)
        self.assertEqual(udfa.membership([0, 1]), Result.accept)
        self.assertEqual(udfa.membership([0, 1, 1]), Result.accept)
        self.assertEqual(udfa.membership([0, 0, 0]), Result.reject)
        self.assertEqual(udfa.membership([0, 1, 1, 1, 1, 1]), Result.accept)
Esempio n. 9
0
 def test_del_unreachable_states(self):
     alphabet = ["a", "b"]
     s = [1, 2, 3, 4, 5]
     transitions = [(1, "b", 1), (1, "a", 2),
                    (2, "a", 3), (2, "b", 4),
                    (3, "a", 4), (3, "b", 3),
                    (4, "a", 2), (4, "b", 1),
                    (5, "a", 2), (5, "b", 3)]
     acc_s = [2, 3]
     rej_s = [4, 5, 1]
     dfa = DFA.build(alphabet=alphabet, states=s, start_state=1,
                     accept_states=acc_s, reject_states=rej_s,
                     transitions=transitions)
     self.assertTrue(5 not in dfa.reachable_states())
     self.assertTrue(dfa.is_complete())
     dfa.del_unreachable_states()
     self.assertTrue(dfa.is_complete())
Esempio n. 10
0
 def test_DFA_numeric_states(self):
     alphabet = ["a", "b"]
     s = [1, 2, 3, 4]
     transitions = [(1, "b", 1), (1, "a", 2),
                    (2, "a", 3), (2, "b", 4),
                    (3, "a", 4), (3, "b", 3),
                    (4, "a", 2), (4, "b", 1)]
     acc_s = [2, 3]
     rej_s = [4]
     dfa = DFA.build(alphabet=alphabet, states=s, start_state=1,
                     accept_states=acc_s, reject_states=rej_s,
                     transitions=transitions)
     self.assertEqual(dfa.membership(""), Result.neutral)
     self.assertEqual(dfa.membership("a"), Result.accept)
     self.assertEqual(dfa.membership("ab"), Result.reject)
     self.assertEqual(dfa.membership("abb"), Result.neutral)
     self.assertEqual(dfa.membership("aba"), Result.accept)
     self.assertEqual(dfa.membership("abaab"), Result.accept)
Esempio n. 11
0
 def test_equivalence(self):
     a = "a"
     b = "b"
     alphabet = [a, b]
     s = [10, 1, 2, 3, 4, 5, 6]
     transitions = [(10, a, 10), (10, b, 10),
                    (1, a, 2), (1, b, 5), (2, a, 3), (2, b, 10), (3, a, 3),
                    (3, b, 4), (4, a, 3), (4, b, 10), (5, a, 6), (5, b, 10),
                    (6, a, 10), (6, b, 5)]
     acc_s = [10, 5]
     rej_s = [1, 2, 3, 4]
     dfa = DFA.build(alphabet=alphabet,
                     states=s,
                     start_state=1,
                     accept_states=acc_s,
                     reject_states=rej_s,
                     transitions=transitions)
     # res = self.mat.equivalence_query(dfa)
     self.assertTrue(self.mat.equivalence_query(dfa)[0])
Esempio n. 12
0
 def setUp(self):
     a = "a"
     b = "b"
     alphabet = [a, b]
     s = [10, 1, 2, 3, 4, 5, 6]
     transitions = [(10, a, 10), (10, b, 10),
                    (1, a, 2), (1, b, 5), (2, a, 3), (2, b, 10), (3, a, 3),
                    (3, b, 4), (4, a, 3), (4, b, 10), (5, a, 6), (5, b, 10),
                    (6, a, 10), (6, b, 5)]
     acc_s = [10, 5]
     rej_s = [1, 2, 3, 4]
     dfa = DFA.build(alphabet=alphabet,
                     states=s,
                     start_state=1,
                     accept_states=acc_s,
                     reject_states=rej_s,
                     transitions=transitions)
     # self.dfa2 = copy.copy(dfa).to_reverse_NFA().to_DFA().to_reverse_NFA().to_DFA()
     self.mat = MinAdequateTeacher(dfa)
Esempio n. 13
0
 def setUp(self):
     a = "a"
     b = "b"
     alphabet = [a, b]
     s = [0, 1, 2, 3, 4, 5, 6]
     transitions = [(0, a, 0), (0, b, 0), (1, a, 2), (1, b, 5), (2, a, 3),
                    (2, b, 0), (3, a, 3), (3, b, 4), (4, a, 3), (4, b, 0),
                    (5, a, 6), (5, b, 0), (6, a, 0), (6, b, 5)]
     acc_s = [0, 5]
     rej_s = [1, 2, 3, 4, 6]
     dfa = DFA.build(alphabet=alphabet,
                     states=s,
                     start_state=1,
                     accept_states=acc_s,
                     reject_states=rej_s,
                     transitions=transitions)
     self.dfa2 = dfa.minimize()
     # self.dfa2.write_graphviz("target.txt")
     self.mat = MinAdequateTeacher(dfa)
Esempio n. 14
0
def _build_DFA_from_TSS(alphabet, prefix_set, suffix_set, segment_set,
                        shorts_set):
    name_gen = state_generator()
    alp = set(alphabet)
    start_id = next(name_gen)
    reject = set()
    accept = set()
    tr = collections.defaultdict(lambda: None)
    state_map = {tuple(): start_id}

    prefshorts = prefix_set.union(shorts_set)

    for strng in prefshorts:
        for substrng in prefixes(strng):
            if substrng not in state_map:
                state_map[substrng] = next(name_gen)

    for strng in segment_set:
        if strng[1:] not in state_map:
            state_map[strng[1:]] = next(name_gen)
        if strng[:-1] not in state_map:
            state_map[strng[:-1]] = next(name_gen)

    for strng in prefshorts:
        for pref, sym, suff in prefix_symbol_suffix(strng):
            if not pref:
                tr[start_id, sym[0]] = state_map[sym]
            else:
                tr[state_map[pref], sym[0]] = state_map[pref + sym]

    for strng in segment_set:
        tr[state_map[strng[:-1]], strng[-1]] = state_map[strng[1:]]

    for strng in suffix_set.union(shorts_set):
        accept.add(state_map[strng])

    delta = lambda q, a: tr[q, a]
    return DFA(alp, set(state_map.values()), start_id, accept, reject, delta,
               tr)
Esempio n. 15
0
 def test_del_dead_states(self):
     alphabet = ["a", "b"]
     s = [1, 2, 3, 4]
     transitions = [(1, "b", 1), (1, "a", 2),
                    (2, "a", 3), (2, "b", 4),
                    (3, "a", 4), (3, "b", 3),
                    (4, "a", 2), (4, "b", 1)]
     acc_s = [2, 3]
     rej_s = [4]
     dfa = DFA.build(alphabet=alphabet, states=s, start_state=1,
                     accept_states=acc_s, reject_states=rej_s,
                     transitions=transitions)
     dfa.del_states({4})
     self.assertFalse(dfa.is_complete())
     self.assertEqual(len(set(dfa.itertransitions())), 4)
     dfa.complete(6)
     self.assertTrue(dfa.is_complete())
     self.assertEqual(len(set(dfa.itertransitions())), 8)
     dfa.del_dead_states()
     self.assertTrue(6 not in dfa.states)
     self.assertEqual(len(set(dfa.itertransitions())), 4)
     self.assertFalse(dfa.is_complete())
Esempio n. 16
0
 def test_reversal(self):
     a = "a"
     b = "b"
     alphabet = [a, b]
     s = [0, 1, 2, 3, 4, 5, 6]
     transitions = [(0, a, 0), (0, b, 0),
                    (1, a, 2), (1, b, 5),
                    (2, a, 3), (2, b, 0),
                    (3, a, 3), (3, b, 4),
                    (4, a, 3), (4, b, 0),
                    (5, a, 6), (5, b, 0),
                    (6, a, 0), (6, b, 5)]
     acc_s = [0, 5]
     rej_s = [1, 2, 4, 6]
     dfa = DFA.build(alphabet=alphabet, states=s, start_state=1,
                      accept_states=acc_s, reject_states=rej_s,
                      transitions=transitions)
     rev = dfa.reverse()
     self.assertEqual(rev.membership("ba"), Result.accept)
     self.assertEqual(rev.membership("aaaaaabb"), Result.accept)
     self.assertEqual(rev.membership("ab"), Result.reject)
     self.assertEqual(rev.membership("aba"), Result.accept)
     self.assertEqual(rev.membership("abaab"), Result.accept)