前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >解决多个io流需要关闭而重复嵌套try-catch-finally的问题

解决多个io流需要关闭而重复嵌套try-catch-finally的问题

作者头像
砖业洋__
发布2023-05-06 19:02:04
4210
发布2023-05-06 19:02:04
举报
文章被收录于专栏:博客迁移同步博客迁移同步

问题如图:

相信大多数人都见过如此状态,流多了需要层层关闭,需要层层加上try-catch,为保证下一个流能关闭又要加上finally,烦人!!

我们先来一个测试:

代码语言:javascript
复制
public class Test {
    public static void main(String[] args) {
        try {
            System.out.println("第一try");
            throw new Exception("异常");
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            System.out.println("finally");
            try {
                throw new Exception("又是异常");
            } catch (Exception e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
            System.out.println("会执行吗");
        }
    }
}

运行结果:

提取出重要信息,finally里面可以抓到异常后可以继续往下执行,也就是说finally里面try-catch抓到异常后也必须把这个代码块执行完。

那么有人就写了一个工具类,这种工具类对吗?

代码语言:javascript
复制
public class IOUtil {
    public static void close(Closeable... closeableList) {
        try {
            for (Closeable closeable : closeableList) {
                if (closeable != null){
                    closeable.close();
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

然后

代码语言:javascript
复制
finally{
      IOUtil.close(is, os);
}

看似正确,实则错误!!

如果第一个流关闭的时候异常,那么第二个流close()就不可达,执行不到

这和并列写没区别,如下:

代码语言:javascript
复制
finally{
    try{
          is.close();
          os.close();   // 第一个流关闭出异常第二个流关闭就不可达,执行不到,等于没关
    } catch(Exception e) {
    }
}

那怎么办呢?不能写工具类吗?

不是不能写,而是这种写法是错误的,这种情况下应该把try-catch放在for循环里面,这样才能保证循环会依次关闭流

正确写法1:

代码语言:javascript
复制
public static void close(Closeable... closeableList) {
    for (Closeable closeable : closeableList) {
        try {
            if (closeable != null) {
                closeable.close();
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

然后

代码语言:javascript
复制
finally{
      IOUtil.close(is, os);
}

正确解法2:

代码语言:javascript
复制
public <T extends java.io.Closeable> void close(T t) {
    try {
        if (t != null) {
            t.close();
        }
    } catch (Exception e) {
        e.printStackTrace();
    }
}

然后

代码语言:javascript
复制
finally {
    close(in);
    close(raf);
    close(br);
}

哪怕其中有流关闭出了异常,也不会影响到其他流的关闭,finally{...}里面的东西是要执行完的

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2018-08-09,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
相关产品与服务
腾讯云服务器利旧
云服务器(Cloud Virtual Machine,CVM)提供安全可靠的弹性计算服务。 您可以实时扩展或缩减计算资源,适应变化的业务需求,并只需按实际使用的资源计费。使用 CVM 可以极大降低您的软硬件采购成本,简化 IT 运维工作。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档