原则:最好在任何时候使用InputStream或者OutputStream的时候,在finally中调用close()方法,显式关闭。

一个典型的示例

InputStream in = null;
try {
in = acquireStream();
...
} finally {
if (in != null) in.close();
}

fianlly中的if (in != null) in.close();也可以用IOUtils.closeQuietly(in);代替,需要Apache Commons-IO

为什么需要调用

InputStream的作用是用来表示从不同数据源产生输入的类,这些数据源包括:

  • 字节数组
  • String对象
  • 文件
  • 管道
  • 一个由其他种类的流组成的序列,以便我们可以将他们收集合并到一个流内。
  • 其他数据源,如Internet连接等

通常不使用close会导致内存泄露,垃圾回收机制会回收,但是最好自己显式关闭,这并不是特别关键。

关键是当InputStream的数据源是文件或者Internet连接的时候。

OutputStream的作用是如FileOutStream,当不调用close的时候,不会将缓存刷入文件中。

InputStream的数据源是文件时

一个InputStream会韩勇一个极小的kernel资源,一个低级的file handle。

当打开文件时,将文件读入到InputStream,会对文件加锁。当你不考虑文件加锁。当你需要读取另一个文件的时候,会打开一个新的InputStream,kernel会分配另一个descriptor(文件流),一直累加,而一个进程的文件描述表是优先,到最后文件描述表将用被用完,所以为了以防万一,最好每次使用完之后都加一个close()

测试代码

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream; public class TestInputStream {
public static void main(String[] args) {
// createTestFile();
// testInputStreamWithOutClose();
// testInputStreamWithOneFileWithOutClose();
testInputStreamWithClose();
} /**
* 创建一万个测试文件
*/
public static void createTestFile() {
try {
for (int i = 0; i < 10000; i++) {
FileOutputStream fos = new FileOutputStream(new File(
"/Users/shenpengyan/Documents/workspace/Test/testInputStream/Test" + i));
fos.write(i);
fos.close();
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} /**
* 用不同文件,不使用close,有"Too many open files in system"报错
*/
public static void testInputStreamWithOutClose(){
try {
for (int i = 0; i < 10000; i++) {
FileInputStream fis = new FileInputStream(new File(
"/Users/shenpengyan/Documents/workspace/Test/testInputStream/Test" + i));
System.out.println(fis.toString() + " " + i);
// fis.close();
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} /**
* 用同一个文件,不加close,有"Too many open files in system"报错
*/
public static void testInputStreamWithOneFileWithOutClose(){
try {
for (int i = 0; i < 10000; i++) {
FileInputStream fis = new FileInputStream(new File(
"/Users/shenpengyan/Documents/workspace/Test/testInputStream/Test1"));
System.out.println(fis.toString() + " " + i);
// fis.close();
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} /**
* 加close,无"Too many open files in system"报错
*/
public static void testInputStreamWithClose(){
try {
for (int i = 0; i < 100000; i++) {
FileInputStream fis = new FileInputStream(new File(
"/Users/shenpengyan/Documents/workspace/Test/testInputStream/Test1"));
System.out.println(fis.toString() + " " + i);
fis.close();
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} }

当不使用close()方法时,会有报错:Too many open files in system

java.io.FileInputStream@7e349a0e 6079
java.io.FileNotFoundException: /Users/shenpengyan/Documents/workspace/Test/testInputStream/Test1 (Too many open files in system)
at java.io.FileInputStream.open(Native Method)
at java.io.FileInputStream.<init>(FileInputStream.java:120)
at TestInputStream.testInputStreamWithOneFileWithOutClose(TestInputStream.java:53)
at TestInputStream.main(TestInputStream.java:9)
InputStream的数据源是Internet连接时

这是我实际遇到的情况,实际业务情况为:我需要调用一个图片存储位置,用key读到的图片存到InputStream里面来进行进一步处理,而我忘记了对它进行close,经过测试,处理300左右的请求之后,就不能继续请求了,这是为什么呢?是因为InputStream没有被垃圾回收掉,还一直占用着连接,而图片服务商有连接数限制,导致之后的请求没有返回,被调用的InputStream类如下:

import java.io.FilterInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.SocketException; import org.apache.http.client.methods.CloseableHttpResponse; public class ObjectInputStream extends FilterInputStream { private CloseableHttpResponse httpResponse; public ObjectInputStream(InputStream in, CloseableHttpResponse httpResponse) {
super(in);
this.httpResponse = httpResponse;
} public void close() throws IOException {
this.httpResponse.close();
try {
super.close();
} catch (SocketException e) {
// expected from some implementations because the stream is closed
}
}
}

当没有调用close方法的时候,没有调用httpResponse.close();,连接不会关掉,所以就尴尬了。

理论依据参考:http://stackoverflow.com/questions/26541513/why-is-it-good-to-close-an-inputstream

Java:浅谈InputStream的close方法的更多相关文章

  1. 浅谈 js 字符串 trim 方法之正则篇

    原文:浅谈 js 字符串 trim 方法之正则篇 关于 trim 其实没啥好说的,无非就是去除首位空格,对于现代浏览器来说只是简单的正则 /^\s+|\s+$/ 就可以搞定了.而且支持中文空格   等 ...

  2. 浅谈 js 字符串 search 方法

    原文:浅谈 js 字符串 search 方法 这是一个很久以前的事情了,好像是安心兄弟在学习js的时候做的练习.具体记不清了,今天就来简单分析下 search 究竟是什么用的. 从字面意思理解,一个是 ...

  3. 浅谈 js 对象 toJSON 方法

    前些天在<浅谈 JSON.stringify 方法>说了他的正确使用姿势,今天来说下 toJSON 方法吧.其实我觉得这货跟 toString 一个道理,他是给 stringify 方法字 ...

  4. JAVA IO流 InputStream流 Read方法

    read()首先我们来看这个没有参数的read方法,从(来源)输入流中(读取的内容)读取数据的下一个字节到(去处)java程序内部中,返回值为0到255的int类型的值,返回值为字符的ACSII值(如 ...

  5. [iOS、Unity、Android] 浅谈闭包的使用方法

    前言 我们经常所编程语言的的进步速度是落后于硬件的发展速度的. 但是最近几年,闭包语法在各个语言中都有自己的体现形式,例如 • C语言中使用函数指针作为回调函数的入口: • Java和C#语言中的La ...

  6. java 浅谈web系统当中的cookie和session会话机制

    一 Cookie: 1. Cookie翻译为小甜饼,有一种特殊的味道.cookie主要用来在(浏览器)客户端做记号用的.Cookie不属于java,Cookie是一种通用的机制,属于HTTP协议的一部 ...

  7. 浅谈 String 的 hashCode() 方法

    Java 中 hash 值的含义 hash 值主要是用来在散列存储结构中确定对象的存储地址的,提高对象的查询效率,如HashMap.HashTable等: 如果两个对象相同,那么这两个对象的 hash ...

  8. [Android&amp;Java]浅谈设计模式-代码篇:观察者模式Observer

    观察者,就如同一个人,对非常多东西都感兴趣,就好像音乐.电子产品.Game.股票等,这些东西的变化都能引起爱好者们的注意并时刻关注他们.在代码中.我们也有这种一种方式来设计一些好玩的思想来.今天就写个 ...

  9. 浅谈js的sort()方法

    如果调用该方法时没有使用参数,将按字母顺序对数组中的元素进行排序,说得更精确点,是按照字符编码(字符串Unicode码点)的顺序进行排序.要实现这一点,首先应把数组的元素都转换成字符串(如有必要),以 ...

随机推荐

  1. Android Broadcast Receiver

    说明 有时候我们在做android系统软件的时候,经常会需要做的事就是开机重新设置上次关机前的状态,当然,我们就会用到这个开机广播: <uses-permission android:name= ...

  2. TS 流解码过程

    TS 流解码过程: 1. 获取TS中的PAT 2. 获取TS中的PMT 3. 根据PMT可以知道当前网络中传输的视频(音频)类型(H264),相应的PID,PCR的PID等信息. 4. 设置demux ...

  3. DrawDib函数组的使用

    Microsoft的针对与设备无关位图(DIB位图),在其WIN32 SDK的Multimedia中提供了一组绘制DIB位图的高性能函数组──DrawDib函数组.DrawDib函数组是一组不依赖于图 ...

  4. android view的setVisibility方法值的意思

    android view的setVisibility方法值的意思 有三个值 visibility  One of VISIBLE, INVISIBLE, or GONE. 常量值为0,意思是可见的 常 ...

  5. Java 7爆最新漏洞,10年前的攻击手法仍有效

    英文原文:New Reflection API affected by a known 10+ years old attack 据 SECLISTS 透露,他们发现新的 Reflection API ...

  6. EasyHook远注简单监控示例 z

    http://www.csdn 123.com/html/itweb/20130827/83559_83558_83544.htm 免费开源库EasyHook(inline hook),下面是下载地址 ...

  7. 对LR analysis的平均事务响应时间和summary中时间值不同的解释

    最近在做性能测试对LR结果分析时,又碰到了关于summary里与平均事务响应时间中各交易的响应时间值不同的问题.在此做个记录. 若交易中设置了思考时间,分析时需要注意查看是否过滤思考时间. 设置是否包 ...

  8. bjfu1208 中位数

    题目是给你一个数x以及一个长度为n的数列,让你往数列里插入y个数,使数列的中位数正好是x,求y的最小值.(其实这题的中位数跟数学里的中位数有一点区别,略去不提) 那么就排完序以后分情况讨论一下就好了. ...

  9. 差分信号(Differential Signal)

    差分信号(Differential Signal)在高速电路设计中的应用越来越广泛,电路中最关键的信号往往都要采用差分结构设计,什么另它这么倍受青睐呢?在 PCB 设计中又如何能保证其良好的性能呢?  ...

  10. Eclipse中设置在创建新类时自动生成注释的方法

     windows–>preference Java–>Code Style–>Code Templates code–>new Java files 编辑它 ${filecom ...