【问题标题】:catching exceptions recursively in Java在 Java 中递归地捕获异常
【发布时间】:2014-01-18 15:00:54
【问题描述】:

我目前正在开发一款小游戏,但我遇到了无法自行解决的问题。我有一个方法可以读取输入并将其存储在变量中。对于任何错误的输入,将引发 IllegalArgumentException,您可以在其中再次尝试输入。但是,如果您再次做错了,它将继续进行下一个输入类型。但我希望它要求输入,直到输入有效。我的导师告诉我用我做的 try and catch 来做,但据说它只会做两次然后继续。

代码如下:

 public void readSettings(){
    Scanner userinput = new Scanner(System.in);
    System.out.println("Wie lange soll der Code sein? (4-10):");
    String input = userinput.nextLine();
    //Eingabe der Länge des zu lösenden Codes. Bei einer Eingabe außerhab des Wertebereichs wird dies gemeldet und neu gefragt.
    try{
        if (input.matches("[4-9]|10")) {
            this.codelength = Integer.parseInt(input);  
        }
        else {
            throw new IllegalArgumentException();
        }
    }

    catch (IllegalArgumentException e) {
        System.out.println("Eingabe außerhalb des Wertebreichs!"); 
        //readSettings();
        System.out.println("Wie lange soll der Code sein? (4-10):");
        input = userinput.nextLine();
        if (input.matches("[4-9]|10")) {
            this.codelength = Integer.parseInt(input);  
        }
        else {
            throw new IllegalArgumentException(e);
        }
    } finally {

        System.out.println("Welche Ziffern sind erlaubt? 0- (1-9):");
        input = userinput.nextLine();
        //Hier wird die valuerange(Also die Maximale Zahl in der Reihe) abgefragt. 
        //Auch hier wird eine falche Eingabe abgefangen und der Input neu gestartet. (Leider nicht sehr elegant und benutzerfreundlich.
        try {
            if (input.matches("[1-9]")) {
                this.valuerange = Integer.parseInt(input);  
            }
            else {
                throw new IllegalArgumentException();
            }
        }
        catch (IllegalArgumentException f) {
            System.out.println("Eingabe außerhalb des Wertebreichs!"); 
            //readSettings();
            System.out.println("Welche Ziffern sind erlaubt? 0- (1-9):");
            input = userinput.nextLine();
            if (input.matches("[1-9]")) {
                this.valuerange = Integer.parseInt(input);  
            }
            else {
                throw new IllegalArgumentException(f);
            }
        } finally {

            //Falls der Modus nicht Cpmouter gegen Computer ist, wird ein Spielername mit abgefragt.
            try {
                if(!cpumode) {
                    System.out.println("Spielername:");
                    this.spielername = userinput.nextLine();
                    //Falls kein input bein Namen vorhanden, wird ein Fehler ausgegeben.
                    if (spielername.length()==0) {
                        throw new IllegalArgumentException("Fehler, kein Spielername eingegeben!" );  

                    }     
                }
            } catch (IllegalArgumentException e) {
                System.out.println("Spielername:");
                this.spielername = userinput.nextLine();
                if (spielername.length()==0) {
                    //throw new IllegalArgumentException("Fehler, kein Spielername eingegeben!" );  
                    throw new IllegalArgumentException(e);
                }     

            }   
        }
    }
}       

我希望你能帮助我。谢谢!

【问题讨论】:

  • “但我希望它要求输入直到输入有效” 使用 do/while 结构。
  • @Sikorski 这个问题似乎是关于某人在做作业时遇到的问题。这不是典型的作业直接副本+问号问题之一。
  • 我很好奇你为什么用input.matches("[4-9]|10"),真的有必要吗?

标签: java exception recursion


【解决方案1】:

第一步是要意识到您一直在重复您的“读取代码长度”。这通常意味着两件事:1)您应该将代码提取到一个方法中并多次调用该方法,或者 2)您应该使用循环并在循环中编写代码。 (或两者兼有)

循环的建议应该敲响警钟,因为只有这样(或递归......)才能让您根据需要重复操作非固定次数。在伪代码中:

repeat
    readNumber
until number is valid

如您所见,条件位于循环的底部。在 Java 中,您将使用 do {...} while(...); - 请注意,您必须从伪代码中反转条件,因为它是 while,而不是 until

附带说明,当您自己抛出异常时,您可以跳过抛出,而是将您的 codelength 保留为您认为无效的值,例如-1。无论如何,您都需要它,因为您必须将异常捕获为 readNumber 部分的一部分,该部分仍在您的循环中。

【讨论】:

  • 我已经做到了,就像你用 do{} while() 告诉你的那样:do ask for input and check wehther input is valid if it is, set the variable if not, return an error while the input doesn´t match 但是我在输入某物时确实得到了一个空指针。不匹配。
  • 我无法告诉您为什么没有代码就获得 NPE,但引用我自己的话:“您必须将异常捕获为 readNumber 部分的一部分”。换句话说:不要在循环内抛出异常;请检查您的 codelength 变量
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2011-05-04
  • 2010-12-07
  • 2014-11-02
  • 2018-11-05
  • 1970-01-01
  • 2017-12-27
相关资源
最近更新 更多