diff --git a/src/markov_ketju.py b/src/markov_ketju.py index d7407a7..445b217 100644 --- a/src/markov_ketju.py +++ b/src/markov_ketju.py @@ -16,6 +16,7 @@ class MarkovKetju: raise ValueError("Aste ei voi olla < 1!") self._trie = trie + self._opetusdata = [] self._aste = aste self._menneet_tilat = deque() @@ -25,8 +26,9 @@ class MarkovKetju: ["ABC", "ABB", "AAAAAA"] """ self._trie = Trie() + self._opetusdata = opetusdata - for jono in opetusdata: + for jono in self._opetusdata: if len(jono) > self._aste: alkio = deque(jono[0:self._aste+1]) self._trie.lisaa(alkio) @@ -38,11 +40,20 @@ class MarkovKetju: def aseta_alkuosa(self, alkuosa): """Asettaa alkuosan, jonka perusteella Markovin ketju luo seuraavan merkin. - Alkuosan pituus on sama kuin ketjun aste, liian pitkästä alkuosasta jätetään - loppu pois. + Alkuosan pituus on vähintään yksi, liian pitkästä alkuosasta jätetään + loppu pois. Liian lyhyttä täydennetään opetusdatan perusteella. """ - if len(alkuosa) < self._aste: - raise ValueError("Liian lyhyt alkuosa!") + while len(alkuosa) < self._aste: + ketju = MarkovKetju(len(alkuosa)) + ketju.kasittele_opetusdata(self._opetusdata) + ketju.aseta_alkuosa(alkuosa) + alkuosa = [x for x in alkuosa] + + seuraava = ketju.seuraava() + if not seuraava: + raise ValueError("Alkuosan täydennys ei onnistunut!") + alkuosa.append(seuraava) + self._menneet_tilat = deque([alkuosa[i] for i in range(0, self._aste)]) def seuraava(self): diff --git a/src/tests/markov_ketju_test.py b/src/tests/markov_ketju_test.py index 4426b79..84507e1 100644 --- a/src/tests/markov_ketju_test.py +++ b/src/tests/markov_ketju_test.py @@ -10,6 +10,9 @@ class TestMarkovKetju(unittest.TestCase): ketju = MarkovKetju(1) opetusdata = ["ABCDEA"] ketju.kasittele_opetusdata(opetusdata) + + self.assertRaises(ValueError, ketju.seuraava) + ketju.aseta_alkuosa("E") self.assertEqual("A", ketju.seuraava()) @@ -35,10 +38,25 @@ class TestMarkovKetju(unittest.TestCase): self.assertEqual("E", ketju.seuraava()) self.assertEqual("A", ketju.seuraava()) - self.assertRaises(ValueError, ketju.aseta_alkuosa, "F") ketju.aseta_alkuosa("EF") self.assertFalse(ketju.seuraava()) + def test_alkuosan_taydennys(self): + ketju = MarkovKetju(2) + opetusdata = ["ABCDEAB"] + ketju.kasittele_opetusdata(opetusdata) + + self.assertRaises(ValueError, ketju.aseta_alkuosa, "F") + + ketju.aseta_alkuosa("A") + + self.assertEqual("C", ketju.seuraava()) + self.assertEqual("D", ketju.seuraava()) + self.assertEqual("E", ketju.seuraava()) + self.assertEqual("A", ketju.seuraava()) + self.assertEqual("B", ketju.seuraava()) + self.assertEqual("C", ketju.seuraava()) + def test_seuraava_todennakoisyys(self): """Testaa, että Markovin ketjun antamat merkit ilmenevät likimain oikeilla yleisyyksillä""" ketju = MarkovKetju(1) @@ -64,7 +82,7 @@ class TestMarkovKetju(unittest.TestCase): a_maara += 1 elif merkki == "B": b_maara += 1 - elif merkki == "C": + else: c_maara += 1 a_osuus = a_maara / yhteensa # Pitäisi olla noin 1/6 diff --git a/test.py b/test.py deleted file mode 100644 index b8d5baa..0000000 --- a/test.py +++ /dev/null @@ -1,24 +0,0 @@ -base_str = ''.join(random.choice(string.ascii_lowercase) for i in range(100000000)) -start_time = time.time() -durations = [] - -dictionary = {} - -for i in range(26): - dictionary[string.ascii_lowercase[i]] = i - -start_time = time.time() -result = [] -for c in base_str: - result.append(dictionary[c]) -durations.append(time.time() - start_time) - -start_time = time.time() -result = [] -for c in base_str: - result.append(ord(c)-97) -durations.append(time.time() - start_time) - - - -print(durations)