Java -- 关闭扫描程序和资源泄漏

2022-09-04 04:25:05

我正在学习Java,并从事一些有趣的项目。我遇到的一个问题是,当我使用对象时,Eclipse会警告我:Scanner

资源泄漏:“扫描”永远不会关闭。

因此,我在代码的末尾添加了一个,该代码负责警告。scan.close();

问题来了,因为我在同一个包中还有其他类也使用扫描仪对象,Eclipse告诉我分别关闭这些类中的扫描仪。但是,当我这样做时,它似乎关闭了所有扫描仪对象,并且在运行时遇到错误。

以下是导致错误的原因的示例:

import java.util.Scanner;
public class test2 {
    public static void main(String [] args) {
        Scanner scan = new Scanner(System.in);
        int test = 0;
        do {    
            //Do stuff
            test = scan.nextInt();
            System.out.println(test);

            scanTest scanTest = new scanTest();
            scanTest.test();
        } while (test != 0);

        scan.close();       
    }
}

import java.util.Scanner;
public class scanTest { 
    public void test() {
        Scanner scanner = new Scanner(System.in);
        int blah = scanner.nextInt();
        System.out.println(blah);
        scanner.close();
    }
}

在类中关闭扫描仪并再次输入 do 循环后,该行发生错误scanTesttest2test = scan.nextInt();

我尝试将扫描仪对象的创建移动到do循环中,只是为了每次都创建一个新对象,但错误仍然发生。

不知道为什么会发生这种情况,或者我如何确保我的所有I / O对象都关闭而不会遇到问题。

我遇到的一篇文章提到,当关闭时,我无法重新开放。如果是这种情况,我只需要确保在程序结束时关闭具有 System.in 的扫描仪对象,并在其他类中@suppress所有其他扫描仪警告?还是仍然会让所有这些扫描仪对象保持打开状态(不好)?System.in


答案 1

首先,这是没有内存泄漏。

其次,当您关闭流包装器时,默认实现是让它关闭它包装的流。这意味着,第一次关闭扫描仪时(如所写),是的,您关闭 System.in。

一般来说,如果 System.in 打算再次阅读 System.in,人们希望避免关闭它们。执行此操作的最佳方法取决于您的程序。

可以将 System.in 中的信息复制到某种缓冲区中,然后扫描缓冲区。人们可能不会关闭扫描仪,而是在其他位置重复使用它。甚至可以取消引用扫描程序以进行垃圾回收,并在 System.in 上创建多个新扫描程序。

这些解决方案并不都是等效的,有些被认为比其他解决方案好得多;但是,这完全取决于调用程序。尝试一些,如果遇到问题,请打开一个新的StackOverflow问题,在其中显示代码的相关部分,问题的描述,示例输入和错误的输出(以及所需的输出)。

祝你好运。


答案 2

是的,当您关闭扫描仪时,您将关闭基础流(在本例中为 System.in)。为了避免这种情况,要么创建一个可供所有类使用的扫描仪的全局变量,要么有一个用于关闭扫描仪的中心点(就在程序退出之前是理想的)


推荐