kopia lustrzana https://gitlab.com/4ham/koch-method-real-words
72 wiersze
2.6 KiB
Python
72 wiersze
2.6 KiB
Python
|
import random
|
||
|
import re
|
||
|
|
||
|
def filter_initial(letters, wordlist):
|
||
|
regexp = re.compile(f"[{''.join(letters)}]+")
|
||
|
return [w for w in wordlist if regexp.fullmatch(w)]
|
||
|
|
||
|
def filter(new_letter, old_letters, wordlist):
|
||
|
regexp = re.compile(f"[{''.join(old_letters)}]*{new_letter}[{new_letter}{''.join(old_letters)}]*")
|
||
|
return [w for w in wordlist if regexp.fullmatch(w)]
|
||
|
|
||
|
class WordLottery:
|
||
|
"""This word lottery makes it 20 x less probable
|
||
|
to again draw a word that had already been drawn previously."""
|
||
|
|
||
|
def __init__(self, words):
|
||
|
self.words = words.copy()
|
||
|
self.sub = None
|
||
|
|
||
|
def add(self, word):
|
||
|
self.words.append(word)
|
||
|
|
||
|
def lots(self):
|
||
|
if self.sub:
|
||
|
return len(self.words) + self.sub.lots() / 20
|
||
|
else:
|
||
|
return len(self.words)
|
||
|
|
||
|
def draw(self):
|
||
|
lots = self.lots()
|
||
|
r = random.random()
|
||
|
if r * lots < len(self.words):
|
||
|
draw_i = random.randrange(0, len(self.words))
|
||
|
result_word = self.words[draw_i]
|
||
|
del self.words[draw_i:draw_i+1]
|
||
|
if not self.sub:
|
||
|
self.sub = WordLottery([result_word])
|
||
|
else:
|
||
|
self.sub.add(result_word)
|
||
|
return result_word
|
||
|
else:
|
||
|
if self.sub:
|
||
|
return self.sub.draw()
|
||
|
else:
|
||
|
raise RuntimeError("This was not supposed to happen. r: {r}, lots: {lots}, self.words: {len(self.words}.")
|
||
|
|
||
|
def write_words(filtered, outdir, outname, words_per_lesson, blanks):
|
||
|
lottery = WordLottery(filtered)
|
||
|
with open(f"{outdir}/{outname}", "w") as out:
|
||
|
for _ in range(0, words_per_lesson):
|
||
|
out.write(lottery.draw())
|
||
|
out.write(blanks)
|
||
|
out.write("\n")
|
||
|
|
||
|
def mk_lessons(wordlist, learn_order, outdir, words_per_lesson = 50, blanks=" "):
|
||
|
for lesson_name in learn_order.keys():
|
||
|
if "new_letter" in learn_order[lesson_name]:
|
||
|
old_letters = learn_order[lesson_name]['old_letters']
|
||
|
new_letter = learn_order[lesson_name]['new_letter']
|
||
|
filtered = filter(new_letter, old_letters, wordlist)
|
||
|
else:
|
||
|
letters = learn_order[lesson_name]['letters']
|
||
|
filtered = filter_initial(letters, wordlist)
|
||
|
|
||
|
if "new_words" in learn_order[lesson_name]:
|
||
|
if learn_order[lesson_name]["new_words"] != len(filtered):
|
||
|
raise RuntimeError(f"Lesson {lesson_name}: Wrong word count should: {learn_order[lesson_name]['new_words']} is: {len(filtered)}.")
|
||
|
for i in range(0, 10):
|
||
|
write_words(filtered, outdir, f"{lesson_name}_{i}.txt", words_per_lesson, blanks)
|
||
|
|
||
|
|