当前位置: 首页 > 知识库问答 >
问题:

为什么这段代码会变成无限循环?[复制]

岳宣
2023-03-14

我写了这个简单的代码来获取一个double,并一直询问直到得到一个为止,但是当你给一个string时,它就变成了一个无限循环,我不知道为什么。为什么它会这样?

Scanner scanner = new Scanner(System.in);   
double x = 0.0d;

while (true) {
    try {
        System.out.println("Gimme a double:");

        x = scanner.nextDouble();
        break;
    } catch (InputMismatchException e) {}           
}

System.out.println(x);

共有3个答案

申屠浩歌
2023-03-14

Reimeus正确说明了无限循环发生的原因。您可以通过在catch块中调用scanner.nextLine()来修复它:

public static void main(String[] args) throws IllegalArgumentException,
        IllegalAccessException {
    /*
     * StackTest t = new StackTest();
     * 
     * for(Field f :t.getClass().getDeclaredFields()){
     * System.out.println(f.get(t)); }
     */

    Scanner scanner = new Scanner(System.in);
    double x = 0.0d;

    while (true) {
        try {
            System.out.println("Gimme a double:");

            x = scanner.nextDouble();
            break;
        } catch (InputMismatchException e) {
            scanner.nextLine();
        }
    }

    System.out.println(x);
}
杜浩壤
2023-03-14

根据Scanner#nextDouble的javadocs,如果转换为Double不成功,则不会消耗字符(但如果转换成功,则会消耗字符):

将输入的下一个标记扫描为双精度。如果下一个标记无法转换为有效的双精度值,此方法将抛出InputMismatchException。如果转换成功,扫描仪将前进超过匹配的输入。

您的程序的示例输出:

$ java Main
Gimme a double:
3.5
3.5
$ java Main
Gimme a double:
blah
Gimme a double:
Gimme a double:
Gimme a double:
Gimme a double:
Gimme a double:
Gimme a double:
(Infinite loop here)

您必须自己使用这些字符,最好是在异常处理程序中:

} catch (InputMismatchException e) {
    System.out.println("Not a double: " + scanner.nextLine());
}

已更改程序的输出示例:

$ java Main
Gimme a double:
blah
Skipped Past: blah
Gimme a double:
3.56
3.56
车辰龙
2023-03-14

如果最初输入了无效的< code>double值,就会变成无限循环。控制然后进入异常块。因为< code>Scanner#nextDouble不使用新行字符,所以这些值会重复传递给语句

x = scanner.nextDouble();

它不会阻止已经接收到的输入。这会导致无限循环。

不应使用空的异常块,而应使用 Scanner#nextLine 来使用换行符。

} catch (InputMismatchException e) {
    System.out.println("Error found: " + scanner.nextLine() + " continuing...");
}

这样 Scanner#nextDouble 行将在下一次迭代中阻止 IO

 类似资料:
  • 该程序应该使用int 0x10在ASCII中打印一个具有给定字符的金字塔,3行的预期结果(下面代码中使用的数量)将是: A. a a a a a 要编译和运行代码,我使用nasm编译它,然后使用qemu进行仿真: 然而,程序get无法打印所有ASCII值。此外,如果有任何针对nasm代码的调试器,可以让您逐行运行,允许您检查寄存器值,这对学习也很有帮助。

  • 我有一个看起来很简单的问题,但由于某种原因我无法绕过它。基本上我的程序正在导致一个无限循环,我不知道为什么。 下面是我陷入的特定循环: 当我运行它时,它总是问我输入列#。我给它一个数字,它接受这个数字,$response变为True,但while循环继续运行,就好像<code>的$response</code>为false一样。我是Perl新手,所以可能我遗漏了一些东西,但是($response=

  • 问题内容: 这段代码使我凝视了几分钟: (这里的第137行) 我以前从未见过,而且我也不知道Java有一个“ loop”关键字(NetBeans甚至没有像关键字一样给它上色),并且它在JDK 6中可以很好地编译。 有什么解释? 问题答案: 它不是一个keyword,而是一个label。 用法:

  • 当我开始我的代码 我得到无限循环。为什么?

  • hasNext()的定义是“如果此扫描仪的输入中有另一个标记,则返回true。此方法可能会在等待输入扫描时阻塞。扫描仪不会前进超过任何输入。” 当我把 standardInput.hasNext() 放在 for 循环中时,程序会向无穷大运行。但是如果我把它放在 while-loop 中,它不会运行到无穷大。这两个程序之间的区别在哪里,为什么其中一个有效而另一个无效? for循环: while-l

  • 但是如果我在这个循环中打印了一些内容,那么它就不会终止。为什么会这样?