I'm creating a simple hangman game program where the secret word is selected from a large dictionary (300,000+ words). I'm testing the code with a much smaller dictionary, and one of the things that I want to filter out are any words that contain uppercase letters. I've been trying to do that, but currently my code will only filter out some words that contain or are fully uppercase.
Here's the code:
class Hangman(object):
def __init__(self, level=5, non_ascii=False, dictionary='ezdict.txt', allow_uppercase=False, non_alpha=False):
global os
import os
import random
self.level = level
self.score = 0
self.loss = 6
self.wordbank = []
self.used_letters = []
self.game_dict = []
self.empty_gallows = " _____\n | |\n |\n |\n |\n |\n |\n |\n_|_________\n|/ \|\n| |"
self.first_gallows = " _____\n | |\n | O\n |\n |\n |\n |\n |\n_|_________\n|/ \|\n| |"
self.second_gallows = " _____\n | |\n | O\n | |\n |\n |\n |\n |\n_|_________\n|/ \|\n| |"
self.third_gallows = " _____\n | |\n | O\n | /|\n |\n |\n |\n |\n_|_________\n|/ \|\n| |"
self.fourth_gallows = " _____\n | |\n | O\n | /|\\\n |\n |\n |\n |\n_|_________\n|/ \|\n| |"
self.fifth_gallows = " _____\n | |\n | O\n | /|\\\n | /\n |\n |\n |\n_|_________\n|/ \|\n| |"
self.sixth_gallows = " _____\n | |\n | O\n | /|\\\n | / \\\n |\n |\n |\n_|_________\n|/ \|\n| |"
self.gal_list = [self.empty_gallows, self.first_gallows, self.second_gallows, self.third_gallows, self.fourth_gallows, self.fifth_gallows, self.sixth_gallows]
with open(dictionary, 'r') as file:
self.words = file.read().split('\n')
for i in self.words:
if (len(i) <= self.level) and (len(i) > 0):
self.game_dict.append(i)
if non_ascii == False:
for i in self.game_dict:
try:
i.encode('ascii')
except UnicodeEncodeError:
self.game_dict.remove(i)
if non_alpha == False:
for i in self.game_dict:
if i.isalpha() != True:
self.game_dict.remove(i)
if allow_uppercase == False:
for i in self.game_dict:
if any(letter.isupper() for letter in i):
self.game_dict.remove(i)
self.secret_word = random.choice(self.game_dict)
for i in list(self.secret_word):
self.wordbank.append('_')
os.system('clear')
def __play_again(self):
play_again = input("Would you like to play again? Type 'yes' or 'no': ")
if play_again == 'yes':
Hangman().play()
elif play_again == 'no':
os.system('clear')
exit
else:
print('Please check your input and try again.')
self.__play_again()
def play(self): # Think about implementing an option to choose the word
print(self.game_dict) # For Testing
print(self.gal_list[self.score])
print('\n', ' '.join(self.wordbank))
print('\nPREVIOUSLY GUESSED LETTERS:', ' '.join(self.used_letters))
self.__user_input()
def __user_input(self):
print(self.secret_word) # For testing
self.guess = ''
while self.guess == '':
self.guess = input('Guess a letter: ')
if len(self.guess) != 1:
os.system('clear')
print('Please guess a single letter!')
self.play()
elif self.guess in self.used_letters:
os.system('clear')
print('This letter has already been guessed.')
self.play()
elif len(self.guess) == 1:
if self.guess in self.secret_word:
for i in range(len(self.secret_word)):
if self.guess == self.secret_word[i]:
self.wordbank[i] = self.guess
#print(self.wordbank) # For testing
else:
self.score += 1
self.used_letters += self.guess
win_check = ''
for i in self.wordbank:
win_check += i
if win_check == self.secret_word:
os.system('clear')
print("You've won the game!")
self.__play_again()
elif self.score == self.loss:
os.system('clear')
print("Sorry, you've lost this round...")
print('The secret word was ' + str(self.secret_word) + '.')
self.__play_again()
else:
os.system('clear')
self.play()
h = Hangman()
h.play()
The part that is causing issues is this:
if allow_uppercase == False:
for i in self.game_dict:
if any(letter.isupper() for letter in i):
self.game_dict.remove(i)
The text file contains these words, contained in a file called 'exdict.txt':
twinkle
little
star
how
wonder
what
you
are
up
above
the
world
so
high
like
diamond
in
sky
ABC
DEF
XYZ
HIK
bourrées
günter
contraction's
bob's
o'connell
For the uppercase letters, it seems to only check every other word in the list, but I am completely stumped. It should filter out all words with uppercase characters in them, but half of them always remain. This can be seen when it prints out the list of usable words (self.game_dict) upon starting the game.