【问题标题】:How do I create a function that tells me whether a guess has been made before in C Hangman? [closed]如何创建一个函数来告诉我之前是否在 C Hangman 中进行过猜测? [关闭]
【发布时间】:2021-03-23 23:30:54
【问题描述】:

我正在为我的 C 编程任务做一个项目,我必须创建一个简单版本的 Hangman。该程序读取一个文本文件并创建一个包含文本文件内所有单词的链接列表。然后根据用户请求的大小从链表中随机选择一个节点,给用户若干条生命。在那之后,它非常简单。到目前为止,除了一件事之外,我已经让一切都完美地工作(据我所知)。我需要游戏不允许多次猜测同一个字母。我尝试初始化一个每次猜测时递增 1 的猜测计数,以及一个将每个猜测存储在猜测的计数中的数组,然后是一个 for 循环,该循环检查猜测是否等于前面的任何一个猜测存储在数组中。这悲惨地失败了,它很混乱并且完全功能失调,只会告诉我是否在需要时重复了猜测。我现在不知所措。非常感谢任何帮助,请,谢谢! 我的代码有点乱,但是 cmets 应该会让你更清楚一点。

Link to the words.txt file

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>

int nodeNum, chances, misses, score, corrGuess, wordLen = 0, countGs = 0;
char* secret;
char incorrGuess[50], guess, dashes[15], prevGuess[50];



/*Node of linked list*/
typedef struct node {
    char *data;
    struct node *next;
} node;

node *start = NULL;
node *current;

/*Appending nodes to linked list*/
void add(char *line) {

    node *temp = malloc(sizeof(node));
    temp->data = strdup(line);
    temp->next = NULL;
    current = start;

    if(start == NULL) {
        start = temp;
    } else {
        while(current->next != NULL) {
            current = current->next;
        }
        current->next = temp;
    }
}

/*read text file*/
void readfile(char *filename) {
    FILE *file = fopen(filename, "r");

    if(file == NULL) {
        exit(1);
    }

    char buffer[512];

    while(fgets(buffer, sizeof(buffer), file) != NULL) {
        add(buffer);
    }

    fclose(file);
}

/*Set initial dashes string*/
void setInitDash(){
    int i;
    for(i=0; i < strlen(secret)-1; i++){
        dashes[i] = '-';
    }
}

/*Generate random number between 0 and 2999*/
void randNum(int lower, int upper)
{
    srand(time(0));
    nodeNum = (rand() % (upper - lower + 1)) + lower;

}

/*Choose random node based on random number generated and length given by user*/
void chooseRand(struct node* start, int i)
{

    node* p;
    int n;
    p = start;
    for(n = 0; n != nodeNum; n++)
    {
        p = p->next;
    }
    while(strlen(p->data) != i + 1){
        p = p->next;
    }
    if(p->data == NULL){
        printf("\n\n\n\n\n\n\n\n\n\n\n\n\n\n\nProgram has run out of words, please restart later");
        exit(0);
    }
    secret = p->data;
    setInitDash();
}

/*Check guess for correct guess*/
void checkGuess(){

    int i, j = strlen(secret) - 1;
    for(i = 0; i != j; i++){
        if(secret[i] == guess) {
            dashes[i] = guess;
            score++;
            corrGuess++;
        }
    }
}

/*Check if score changes*/
void checkScore(){
    if(score == 0){
        misses++;
        chances--;
        incorrGuess[misses] = guess;
    }
    else{
        score = 0;
    }
    printf("%s", dashes);
}






/*Print current board*/
void printBoard(){
    printf("__________________________________________________________________\n");
    printf("\n\nCurrent Word: ");
    checkGuess();
    checkScore();
    printf("   Chances: %d Incorrect Guesses: ", chances);
    for(int i = 0; i <= misses; i++)
        printf("%c", incorrGuess[i]);
    printf("\nPlease enter your guess: ");
    scanf(" %c", &guess);
    printf("\n__________________________________________________________________\n");
}

/*Function for if player wins*/
void winCase(){
    printf("\n\n\n\n\nGood Job! You have guessed the word correctly. It was %s Restart the program to play again!", secret);
}

/*Function for if player loses*/
void loseCase(){
    printf("\n\n\n\n\nUnfortunately, you have run out of chances. The word to guess was %s.", secret);
}



int main(){
    score = 0;
    corrGuess = 0;
    int stillPlaying = 1;

    printf("Hello User, Welcome to Hangman\nPlease enter word length then number of chances: ");     /*Welcome Message*/
    scanf("%d %d", &wordLen, &chances);

    readfile("words.txt"); /*Readfile and choose random word*/
    randNum(0, 2999);
    chooseRand(start, wordLen);
    printf("%s", secret);   /*Print secret word for easy testing*/
    printf("__________________________________________________________________\n");     /*Print first iteration of the board*/
    printf("\n\nCurrent Word: %s", dashes);
    printf("   Chances: %d Incorrect Guesses: %s", chances, incorrGuess);
    printf("\nPlease enter your guess: ");
    scanf(" %c", &guess);
    printf("\n__________________________________________________________________\n");
    while(stillPlaying == 1){       /*While loop to print board until win or lose case is true*/
        printBoard();
        if(corrGuess == strlen(secret) - 2){
            stillPlaying = 2;
        }
        else if(chances == 0){
            stillPlaying = 0;
        }
    }
    if(stillPlaying == 0){
        loseCase();
    }
    else if(stillPlaying == 2){
        winCase();
    }



    return 0;
}

【问题讨论】:

  • 为什么用“链表”标记问题? Hangman 中的猜测来自有限的字母表(36 个字母/数字?)......布尔数组或位图不是更好吗?
  • @Myst:这里似乎没有足够的逻辑。是的,我抱怨代码太多的东西丢失了一些东西,但我无法取得进展。放弃。
  • 我的作业必须使用链表

标签: arrays c linked-list


【解决方案1】:

您将创建一个类似 bool guessed[256]; 的数组(char 有 256 个可能的值),并确保所有值都是 0。然后,当进行猜测时,将 guessed[guessedChar] 设置为 1。然后检查如果猜到你会使用if (guessed[charToCheckIfGuessed]) { ... }。我不明白你为什么要尝试使用链表,你真的只是给自己一个比你需要的更难的时间。

这不仅比 for 循环快,而且据我了解,它应该可以正常工作。

【讨论】:

  • 就像我说的,我必须这样做,因为这是我的作业要求
  • @OmarAbzd 尽管如此,我认为你应该试试这个
猜你喜欢
  • 2021-09-30
  • 2022-01-23
  • 2023-03-09
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多