【问题标题】:Problems with a word guessing game猜词游戏的问题
【发布时间】:2013-10-20 05:48:37
【问题描述】:

我试图让 Java 将 while 循环的输出识别为变量,并在进一步的操作中使用该输出。

我想尝试升级它,让一个玩家设置单词,另一个玩家猜测它。问题在于使破折号的数量等于玩家输入的单词中的字母数量,所以我将代码分开,这很有效。

但是当我把它全部放回main 时,它无法识别循环结束后有多少破折号;它只识别只有 1 个破折号的初始破折号,因此会出现问题。

编辑:非常感谢你们,这是我第一次在堆栈溢出,tnx 再次。 像魅力一样工作:D

package iB;
import java.util.Scanner;
 import java.lang.String;
 public class WordGuess {
/**
 * @param args
 */
public static void main(String[] args) {
    Scanner input = new Scanner(System.in);
    String secretWord ;
    String guess, dash = "-", upWord;
    int numGuesses = 0;
    int numWord;
    final String SENTINEL = "!";
    System.out.println("Player 2, please look away.    Player 1, please enter  the secter word: \n");
    secretWord = input.next().toUpperCase().trim();
    numWord = secretWord.length();
    //System.out.println("\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n");   
    for(int dashNum = 1; dashNum < numWord; dashNum++) {
        dash += "-" ;
    }
    System.out.println("WordGuess game!\n");
    do {
        System.out.println("Enter a letter (" + SENTINEL + "to guess entire word): ");
        guess = input.next().toUpperCase().trim();
        numGuesses ++;
      if (secretWord.contains(guess) && guess.length() == 1)    {
            upWord = dash.substring(0, secretWord.indexOf(guess));
            upWord += guess;
            upWord += dash.substring(secretWord.indexOf(guess) + 1, dash.length());
            dash = upWord.toUpperCase();
            System.out.println(dash);
            if (dash.equals(secretWord))    {
                System.out.println("You won!\n" + "The secret word is " + secretWord);
                System.out.println("You made " + numGuesses + " guesses."); }
      } else    if (guess.length() >= 2)    {
            System.out.println("Please only enter one letter at a time! \n");   }               
            if (guess.contains(SENTINEL)) {
            System.out.println("What is your guess? ");
            guess = input.next().toUpperCase().trim();
            if (guess.equals(secretWord))   {
                System.out.println("You won!\n" + "The secret word is " + secretWord);
                System.out.println("You made " + numGuesses + " guesses.");
                break;
            } else {
                System.out.println("You Lose!");
                System.out.println("The secret word was " + secretWord);
                System.out.println("You made " + numGuesses + " guesses.");
                    break;
                }
            }
        }   while(!guess.contains(SENTINEL));
        input.close();  
}

}

【问题讨论】:

  • 好的,这里有一个承诺,就是说 - 最好缩小已完成的代码一点 - 即发布重要的代码.. 省略填充代码
  • 还要确保找出问题所在,而不是发布大量代码。如果您发布更简洁的代码量,那么您将收到更准确和及时的答案。

标签: java


【解决方案1】:

问题

以下代码似乎试图显示在单词中的哪个位置可以找到正确选择的字母

    if (SecretWord.indexOf(guess) >= 0) {
        UpWord = dash.substring(0, SecretWord.indexOf(guess));
        UpWord += guess;
        UpWord += dash.substring(SecretWord.indexOf(guess) + 1, dash.length());
        System.out.println(UpWord);
    } else {

所以如果这个词是this 而你猜到了i 那么输出应该是

--i-

dash.substring 重复破折号,它需要破折号的子部分,因为破折号是1个字母长,除了substring(0,1)之外的任何东西都会导致异常。

基本解决方案

我相信你想重复dash,直到你找到猜到的字母,然后在它之后直到单词的结尾。大致如下:

        if (SecretWord.indexOf(guess) >= 0) {
            int guessedIndex=SecretWord.indexOf(guess);

            String outString="";

            for(int i=0;i<guessedIndex;i++){
                outString+=dash; //repeat dash until we get to the correctly guessed letter
            }

            outString+=guess; //put the letter in

            for(int i=guessedIndex;i<SecretWord.length();i++){
                outString+=dash; //repeat dash until we get to end of the word
            }

            System.out.println(outString);
        } else { 

更好的解决方案

然而,这留下了只显示字母的第一个实例的问题。这可以使用另一个stack overflow answer 来解决,我们看到我们可以使用函数获取一个字符的所有出现

public static ArrayList<Integer> getAllIndexes(String testChar, String string){
    int index=string.indexOf(testChar);


    ArrayList<Integer> indexes=new ArrayList<Integer>();
    while(index>0){
        indexes.add(index);
        index=string.indexOf(testChar,index+1);
    }

    return indexes;
}

然后使用该函数查找所有字母出现的索引,我们可以处理重复的字母

        if (SecretWord.indexOf(guess) >= 0) {
            int guessedIndex=SecretWord.indexOf(guess);

            ArrayList<Integer> indexes=getAllIndexes(guess,SecretWord);

            String outString="";

            for(int i=0;i<SecretWord.length();i++){
                if (indexes.contains(i)){ 
                    outString+=guess; //if its one of the guessed letters, put that in
                }else{
                    outString+=dash; //otherwise add a dash
                }

            }



            System.out.println(outString);
        } else {

现在hello 的一个词和l 的猜测正确输出--LL-

注意事项

  • 通常遵循变量名的命名约定 在小写驼峰式中,表示它们以小写字母开头,如 这样的SecretWord 应该是secretWord。正如目前所写 看起来 SecretWord 是一个类,通常写在 驼峰式大写。
  • 如果你猜到了一个字母,它会停止输入破折号并在之后每次都开始输入该字母,这可以通过使用布尔数组来检查该字母是否已被猜到了,但这超出了这个问题的范围
  • 所有这些解决方案都附加了字符串,这对于大量数字可能会很慢,在您的情况下,这是正确的做法,但是正在将大量字符串连接到一个循环中,请考虑使用StringBuilder 以消除创建大量中间字符串的开销

【讨论】:

  • 谢谢大家,帮了大忙!
【解决方案2】:

解决方案

如果密码是pony,则字符串dash应该等于----。问题是你从来没有真正改变dash 等于-。因此,当您执行dash.substring(SecretWord.indexOf(guess) + 1, dash.length()) 之类的操作时,会出现错误,因为dash 仅包含一个字符。以下是我如何使dash 与秘密词的长度相同:

    for(int i = 0; i < NumWord; i++) {
        dash += "-";
    }

将这一更改直接插入到您的 do-while 循环之前,您的程序就像一个魅力。为了进一步改进您的计划,以下是需要考虑的其他一些事项。

提高可读性

  1. Java 约定规定方法和变量名称的第一个单词是小写的。所以NumWord 应该是numWordSecretWord 应该是secretWord,等等。
  2. SecretWord.indexOf(guess) &gt;= 0 应改为 SecretWord.contains(guess)

游戏建议

  1. 就像在hang man 中一样,您可能应该显示猜到的字母出现的所有位置。例如,如果密码是happy,则猜测p 应该会产生--PP- 的输出,而不是--P--

  2. 作为一项规则,即使不会导致错误,也永远不要接受错误的输入。该程序不应允许以下任何情况:

    • 用户输入一个包含非字母字符或多个单词的字符串作为密码
    • 猜测时输入非字母字符(!除外)
    • 猜字母时,输入多个字符。

【讨论】:

    【解决方案3】:

    我对您的代码进行了一些修改,现在似乎可以正常工作了。 不过,首先,我添加了一个额外的方法,只是为了让它更容易一点:

    public static String printOutWord(String[] UpWord){
        String out = "";
        for(int i = 0; i < UpWord.length; i++){
            out += UpWord[i];
        }
        return out;
    }
    

    以下是对代码的最初几处更改:

    String[] UpWord = new String[NumWord];
        for(int i = 0; i < NumWord; i++){
            UpWord[i] = "-";
        }
    printOutWord(UpWord);
    System.out.println("\nWordGuess game!");
    

    因此,您不再需要变量dash,变量UpWord 已更改为字符串数组。

    剩下的就这些了:

     do {
                System.out.println("Enter a letter (! to guess entire word): ");
                guess = input.next().toUpperCase().trim();
                Numguesses++;
                if(guess.length() > 1){
                    System.out.println("Please only enter one letter at a time");
                }else if (SecretWord.indexOf(guess) >= 0) {
                    int index = SecretWord.indexOf(guess);
                    UpWord[index] = guess;
                    while(SecretWord.indexOf(guess, index+1) >= index){
                        index = SecretWord.indexOf(guess, index+1);
                        System.out.println(index);
                        UpWord[index] = guess;
                    }
                    System.out.println(printOutWord(UpWord));
                    if(printOutWord(UpWord).equals(SecretWord)){
                        System.out.println("You won!\n" + "The secret word is " + SecretWord);
                        return;
                    }
                } else {
                    if (guess.contains("!")) {
                        System.out.println("What is your guess? ");
                        guess = input.next().toUpperCase();
                        if (guess.equals(SecretWord)) {
                            System.out.println("You won!\n" + "The secret word is " + SecretWord);
                            System.out.println("You made " + Numguesses + " guesses");
                        } else if (!guess.equals(SecretWord)) {
                            System.out.println("You Lose!");
                            System.out.println("You made " + Numguesses + " guesses");
                        }
                    }
                }
            } while (!SecretWord.equals(guess));
            input.close();
        }
    

    大部分更改都在第一个 if 语句中。 我希望这会有所帮助,如果需要任何澄清,请问,我很乐意提供帮助:)

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2020-11-22
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-04-24
      • 1970-01-01
      • 2021-05-29
      相关资源
      最近更新 更多