-
Notifications
You must be signed in to change notification settings - Fork 1
/
main.py
134 lines (105 loc) · 4.13 KB
/
main.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
import string
import random
from collections import defaultdict
with open("wordle-answers-alphabetical.txt", "r") as file:
words = file.readlines()
# Computes probability for all letters and returns words which contain them.
def rebalance(probs={}, numPasses=0):
if probs:
for key, val in probs.items():
letterProbabilites[key] = val
totalLetters = sum(letterProbabilites.values())
for key in letterProbabilites.keys():
letterProbabilites[key] = letterProbabilites[key] / totalLetters
mostProbableKeys = sorted(letterProbabilites, key=letterProbabilites.get, reverse=True)
if numPasses == 0:
topKeys = frozenset(mostProbableKeys[:15])
else:
topKeys = frozenset(mostProbableKeys[:15+numPasses])
wordList = []
for letter in mostProbableKeys:
for word in wordsAsLetters.keys():
if word.issubset(topKeys):
mostProbableWord = wordsAsLetters[word]
wordList.extend(mostProbableWord)
if len(wordList) != 0:
break
else:
topKeys.add(letter)
return wordList
def validateWord(word, wordList, numPasses=0):
validatedWordList = []
# Record letters that can't be at given index.
for ind, letter in enumerate(list(word)):
if letter.islower():
lettersNotAtInd[ind].append(letter)
for w in wordList:
badWord = False
# Makes sure the words contain all the known (yellow) letters
for letter in lettersInWord:
if letter not in w:
badWord = True
# Remove word if letters are not correct position
for ind, letter in enumerate(list(word)):
if letter.isupper() and w[ind] != letter.lower():
badWord = True
elif letter.islower() and w[ind] in lettersNotAtInd[ind]:
badWord = True
else:
pass
if not badWord:
validatedWordList.append(w)
# If no words are found, increment counter
if len(validatedWordList) == 0:
numPasses += 1
return numPasses, validatedWordList
def getMoreWords(history, prevList, numPasses=0):
numPasses += 1
wordList = rebalance(numPasses=numPasses)
numPasses, validatedList = validateWord(history[-1], wordList)
while len(validatedList) == 0 or prevList == validatedList:
numPasses += 1
wordList = rebalance(probs, numPasses)
numPasses, validatedList = validateWord(history[-1], wordList, numPasses)
return numPasses, validatedList
letterProbabilites = {key: 0 for key in list(string.ascii_lowercase)}
lettersNotAtInd = d = [[] for x in range(5)]
lettersInWord = set([])
wordsAsLetters = defaultdict(list)
fiveLetterWords = [word.strip('\n') for word in words if len(word) == 6]
for word in fiveLetterWords:
wordsAsLetters[frozenset(word)].append(word)
for letter in list(word):
letterProbabilites[letter] += 1
wordList = rebalance()
history = []
numPasses = 0
while(True):
word = list(input("Whats the result? Lowercase if wrong position, Uppercase if correct, Underscore if unknown. "
"If no words, hit enter and if finished, type done.\n"))
if not word:
numPasses, validatedList = getMoreWords(history, validatedList, numPasses)
continue
elif word == list("done"):
exit()
else:
pass
history.append(word)
wrongLetters = list(input("Wrong Letters?\n"))
probs = {}
for letter in word:
if letter == "_":
pass
else:
lettersInWord.add(letter.lower())
probs[letter.lower()] = 10
for letter in wrongLetters:
probs[letter] = 0
numPasses = 0
wordList = rebalance(probs, numPasses)
numPasses, validatedList = validateWord(word, wordList)
while len(validatedList) == 0:
wordList = rebalance(probs, numPasses)
numPasses, validatedList = validateWord(word, wordList, numPasses)
random.shuffle(validatedList)
print("Possible words:", sorted(validatedList, key=lambda x: len(set(x)), reverse=True), "\n")