io分类
按照流类型 :字符流,字节流
字符流因为数据编码不同,从而有了对字符进行高效操作的流对象,本质就是基于自己流读取时,去查了指定的码表
不同:读写单位不同,处理对象不同
按照方向:输入流,输出流
输入流读操作,输出流写操作
这里以一个具体案例来讲一下 FileInputStream,InputStreamReader,BufferedReader之间的区别,并类比输出流
FileInputStream fis = null; InputStreamReader isr = null; BufferedReader br = null; //用于包装InputStreamReader,提高处理性能。因为BufferedReader有缓冲的,而InputStreamReader没有。 try { String str = ""; fis = new FileInputStream(file);// FileInputStream // 从文件系统中的某个文件中获取字节 isr = new InputStreamReader(fis, "utf-8");// InputStreamReader 是字节流通向字符流的桥梁, br = new BufferedReader(isr);// 从字符输入流中读取文件中的内容,封装了一个new InputStreamReader的对象 int i = 0; while ((str = br.readLine()) != null) { String str1 = str; System.out.println(str1);// 打印出str1 } // 当读取的一行不为空时,把读到的str的值赋给str1 } catch (FileNotFoundException e) { System.out.println("找不到指定文件"); } catch (IOException e) { System.out.println("读取文件失败"); } finally { try { br.close(); isr.close(); fis.close(); // 关闭的时候最好按照先后顺序关闭最后开的先关闭所以先关s,再关n,最后关m } catch (IOException e) { e.printStackTrace(); } }
首先创建一个文件File,然后创建一个FileInputStream 文件输入流,FileInputStream 继承自InputStream上图所示。官方描述:
“从文件系统中的某个文件中获得输入字节,用于读取诸如图像数据之类的原始字节流。要读取字符流,请考虑使用 FileReader
”
原始的字节流需要转化为字符流才能被我们使用,这个时候就需要一个字节流转化为字符流的桥梁,这个就是InputStreamReader 可以读取字符
new InputStreamReader(fis, "utf-8")为了提供字符输入流的读取速度,使用了BufferedReader。看一下官方解释:
“从字符输入流中读取文本,缓冲各个字符,从而实现字符、数组和行的高效读取。
可以指定缓冲区的大小,或者可使用默认的大小。大多数情况下,默认值就足够大了。
通常,Reader 所作的每个读取请求都会导致对底层字符或字节流进行相应的读取请求。因此,建议用 BufferedReader 包装所有其 read() 操作可能开销很高的 Reader(如 FileReader 和 InputStreamReader)。例如,
BufferedReader in
= new BufferedReader(new FileReader("foo.in"));
将缓冲指定文件的输入。如果没有缓冲,则每次调用 read() 或 readLine() 都会导致从文件中读取字节,并将其转换为字符后返回,而这是极其低效的。
通过用合适的 BufferedReader 替代每个 DataInputStream,可以对将 DataInputStream 用于文字输入的程序进行本地化。”
简单描述一下:
1、FileInputStream 从文件中生成的文件字节流
2、用InputStreamReader 将字节流按照指定编码转化为特定的字符流
3、为了避免每次都要从文件读取字符,使用了bufferedReader进行读取。BufferedReader里面有一个默认大小的字符数组
写文件的过程也大致一样。
另外如果只是对字节流的处理,是没有后面两个步骤的。比如从文件读入一些字节流,然后通过流发送的服务端,服务端在进行收到字节码进行相应的操作。