突泉县 浦江县 都江堰市 漳浦县 分宜县 山西省 六枝特区 黎川县 米林县 皋兰县 连州市 崇州市 彰化县 昔阳县 铁岭县 亚东县

当前位置:大秦帝国之纵横>无耻家庭

非诚勿扰

标签:甲壳虫 麻将幻想曲3

书名:性爱大师|作者:笑无语|本书类别:古言|更新时间:2019-07-17 03:16:59|字数:3896字

scanner错误关闭导致的异常

public class test2 {

  public static void main(String[] args) {
    Scanner scanner1 = new Scanner(System.in);
    System.out.println("run scanner1.close()");
    scanner1.close();

    Scanner scanner2 = new Scanner(System.in);
    System.out.println("run scanner2.nextLine()");
    scanner2.nextLine();

  }
}

但是会在scanner2.ne一拳超人_2018年最新新闻网xtLine()调用时抛出异常
java.util.NoSuchElementException: No line found

原因

下面是scanner的源码

// The input source
    pr脱颖而出_2018年最新新闻网ivate Readable source;
public void close() {
        if (closed)
            return;
        if (source instanceof Closeable) {
            try {
                ((Closeable)source).close();
            } catch (IOException ioe) {
                lastException = ioe;
            }
        }
        sourceClosed = true;
        source = null;
        closed = true;
    }

所以调用close方法并不仅仅关闭scanner类,同时关闭了初始化时作为参数传入的Readable对象。
在示例代码中scanner1.close();关闭了System.in,所以虽然初始化scanner2没有问题,但是readLine()会报错。

是否可以通过重新开启System.in的方式补救呢?

遗憾的是,至少作为java的使用者来说是不可以的,除非我们能控制jvm运行。
这涉及到System.in是如何开启的,简单来说因为System.in是特殊的系统资源,由jvm负责开启,无法通过java代码重新初始化System.in。
如果查看System.in的代码我们就能发现它通过native方法实现初始化,在native方法中将控制台或文件句柄传输给System.in来完成。
同样的,Systerm.out System.err也是无法重新被开启的资源,对于它们,close方法应该被谨慎的调用。
(ps:实际上有什么原因关闭呢?)

让我们把问题拓展开来

实际上,所有的能够以System.in/out/err为构造器参数的包装器类的close方法都应该被考虑,
可以看到jdk的设计者并没有区别对待普通的流和System.in/out/err,
而包装器类的close方法关闭底层流对于普通流来说是很合理的,因此我们可以推测事实上其他的包装器的close方法也可能导致关闭System.in/out/err。
常用的bufferinputstream就是如此。

j昆仑决_2018年最新新闻网dk7引入的带资源的try语法糖产生隐蔽的问题

jdk7引入的带资源的try语法糖隐式的帮助程镜花缘_2018年最新新闻网序员调用close方法,
遗憾的是该方法也会产生上述问题,甚至更难被发现。

我们有必要积极的关闭不再需要的流嘛?如何对待io.close?如何预防该问题?

从性能的角星之声_2018年最新新闻网度来说,积极关闭流是必须的,实际上如果我们使用findbugs等代码规范工具,能发现关闭io是被强烈推荐的。
如果你使用idea的话,建议在close之前,使用快捷键ctrl+b进入close方法的源代码来查看其关闭机制。这种方法非常简便,当然eclipse应该也有插件可以实现类似功能。
我们也可以通过包装System.in/out/err来安全的使用它们,实际上利用装饰器模式,覆盖System.封神演义_2018年最新新闻网in/out/err的close方法即可。

打赏
神奇推荐位
  • 中国银行外汇牌价

    灯盏香客 / 著

    “衡大叔,大家都说三十来岁正是男人如狼似虎的年纪”“所以呢?”“我觉得这句话说得很对...

  • 吉林大学

    浮梦公子 / 著

    其实这不过是一场由腹黑皇帝和狡黠恶女定下的一个约盟继而引发的一个故事!人人皆道,将军...

  • 苏州博物馆

    暮夜寒 / 著

    【种田】+【空间】+【温馨】+【致富】+【虐渣】被炸成灰灰的莫颜重生到了古代,成了正...

  • 阿里旺旺

    悠然世 / 著

    本书出版名《美人思无邪》,天猫购买地址=a1z10.1-b.w11350767-15...