patterncppMinor
A different way to execute a hangman game
Viewed 0 times
wayhangmandifferentgameexecute
Problem
Most hangman implementations I have seen keep a list of characters the player has already guessed and compares them to the players current guess each time to see if they have already made the same guess. My implementation checks if the word was changed after replacing any matches. Is my implementation easier to understand as well as more efficient than this one Hangman game logicistics and cleanliness?
Side Question: Should I use static variables in loops?
Hangman
```
#include
#include
#include
#include
#include
#include
std::string replace_if_match(std::string& write, const std::string& read, const std::string& match)
{
assert( write.length() >= read.length() );
for( int search_pos{0}; (search_pos = read.find( match, search_pos )) != -1; ++search_pos){
write.replace( search_pos, match.length(), match );
}
return write;
}
int main()
{
std::ifstream file("word_list");
assert( file.is_open() );
std::vector word_list;
while( !file.eof() ){
static std::string word;
file >> word;
word_list.push_back( word );
}
file.close();
std::random_device rd;
std::mt19937 mt(rd());
std::uniform_int_distribution dist(0, word_list.size() - 1);
std::string unknown_word;
std::string previous_word;
std::string guessed_word;
std::string guess;
int num_of_guesses;
int in_game{true};
while( in_game )
{
unknown_word = word_list[dist(mt)];
guessed_word = std::string().append( unknown_word.length(), '_' );
num_of_guesses = 5;
while( num_of_guesses > 0 && unknown_word != guessed_word )
{
std::cout > guess;
previous_word = guessed_word;
if( previous_word == replace_if_match( guessed_word, unknown_word, guess ) ){
num_of_guesses--;
}
}
if( guessed_word == unknown_word ){
std::cout \n";
std::cin >> in_game;
Side Question: Should I use static variables in loops?
Hangman
```
#include
#include
#include
#include
#include
#include
std::string replace_if_match(std::string& write, const std::string& read, const std::string& match)
{
assert( write.length() >= read.length() );
for( int search_pos{0}; (search_pos = read.find( match, search_pos )) != -1; ++search_pos){
write.replace( search_pos, match.length(), match );
}
return write;
}
int main()
{
std::ifstream file("word_list");
assert( file.is_open() );
std::vector word_list;
while( !file.eof() ){
static std::string word;
file >> word;
word_list.push_back( word );
}
file.close();
std::random_device rd;
std::mt19937 mt(rd());
std::uniform_int_distribution dist(0, word_list.size() - 1);
std::string unknown_word;
std::string previous_word;
std::string guessed_word;
std::string guess;
int num_of_guesses;
int in_game{true};
while( in_game )
{
unknown_word = word_list[dist(mt)];
guessed_word = std::string().append( unknown_word.length(), '_' );
num_of_guesses = 5;
while( num_of_guesses > 0 && unknown_word != guessed_word )
{
std::cout > guess;
previous_word = guessed_word;
if( previous_word == replace_if_match( guessed_word, unknown_word, guess ) ){
num_of_guesses--;
}
}
if( guessed_word == unknown_word ){
std::cout \n";
std::cin >> in_game;
Solution
I find this function signature quite confusing:
The names write, read, and match aren't very descriptive and everything is being passed in by reference, so what is it going to be returning?
Changing the parameter names to something like guessed_word, word_to_guess and guess might be more descriptive. The return still feels wrong though, why not just have it return true/false to indicate if replaces have been made?
The implementation you've made doesn't really conform to the standard rules of Hangman. One of the advantages of keeping track of characters guessed is that it ensures you only guess one character at a time. With your current approach, it's possible to guess partial words (so you can guess 'hang' and it would find the start of 'hangman'). Character matching also encourages you to think about casing,
std::string replace_if_match(std::string& write,
const std::string& read, const std::string& match)The names write, read, and match aren't very descriptive and everything is being passed in by reference, so what is it going to be returning?
Changing the parameter names to something like guessed_word, word_to_guess and guess might be more descriptive. The return still feels wrong though, why not just have it return true/false to indicate if replaces have been made?
The implementation you've made doesn't really conform to the standard rules of Hangman. One of the advantages of keeping track of characters guessed is that it ensures you only guess one character at a time. With your current approach, it's possible to guess partial words (so you can guess 'hang' and it would find the start of 'hangman'). Character matching also encourages you to think about casing,
'H' != 'h' with your current approach. These choices may be intentional, but it feels unexpected.Code Snippets
std::string replace_if_match(std::string& write,
const std::string& read, const std::string& match)Context
StackExchange Code Review Q#129046, answer score: 2
Revisions (0)
No revisions yet.