美文网首页java.io源码解析
java.io源码解析(二)--文件操作(FileInputSt

java.io源码解析(二)--文件操作(FileInputSt

作者: dark丶Night | 来源:发表于2019-05-28 16:05 被阅读0次

声明:本系列只供本人自学使用,勿喷。

实际开发中最常用的就是文件IO,通常情况下,操作二进制文件用字节流,文本文件用字符流。

一、文件字节流

1.FileInputStream

  • 构造器
//实际调用FileInputStream(File file)
public FileInputStream(String name) throws FileNotFoundException
public FileInputStream(File file) throws FileNotFoundException{
    1.文件安全及权限检查
    2.创建FileDescriptor实例来表示文件连接
    3.native方法open
}
// 使用文件系统的现有文件连接来创建
public FileInputStream(FileDescriptor fdObj)
  • 核心方法

核心:私有的本地readBytes方法

private native int readBytes(byte b[], int off, int len) throws IOException;

public int read(byte b[]) throws IOException
public int read(byte b[], int off, int len)

public void close() throws IOException
  • 其他方法
public native long skip(long n) throws IOException;
public native int available() throws IOException;
public final FileDescriptor getFD() throws IOException
public FileChannel getChannel()

2.FileOutputStream

  • 构造器
//实际调用FileOutputStream(File file, boolean append) 
public FileOutputStream(String name) throws FileNotFoundException
public FileOutputStream(String name, boolean append)
public FileOutputStream(File file) throws FileNotFoundException

public FileOutputStream(File file, boolean append) throws FileNotFoundException{
    1.文件安全及权限检查
    2.创建FileDescriptor实例来表示文件连接
    3.native方法open
}
// 使用文件系统的现有文件连接来创建
public FileOutputStream(FileDescriptor fdObj)
  • 核心方法

核心:私有的本地writeBytes方法

private native void writeBytes(byte b[], int off, int len, boolean append)

public void write(byte b[]) throws IOException
public void write(byte b[], int off, int len)

public void close() throws IOException
  • 其他方法
public final FileDescriptor getFD() throws IOException
public FileChannel getChannel()

3.demo

最常见的功能:用FileInputStream和FileOutputStream复制文件

注:JDK7新增try-with-resources语法,将资源放入try()内,就不用手动close()了。

    try (
                InputStream is = new FileInputStream("D:\\fileTest\\app.properties");
                // InputStream is=new FileInputStream(new File("D:\\fileTest\\app.properties"));
                OutputStream os = new FileOutputStream("D:\\fileTest\\out.properties");
        ) {
            byte[] bytes=new byte[1024];
            int len=0;
            while ((len=is.read(bytes))!=-1){
                os.write(bytes,0,len);
            }
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }

二、文件字符流

在研究FileReader和FileWriter之前,有必要先了解其父类。

1.InputStreamReader

底层StreamDecoder

  • 构造器(必须以InputStream为入参)
// 实际调用 StreamDecoder的构造器
public InputStreamReader(InputStream in)
public InputStreamReader(InputStream in, String charsetName)
public InputStreamReader(InputStream in, Charset cs)
public InputStreamReader(InputStream in, CharsetDecoder dec)
  • 核心方法

核心:read到字符数组

public int read(char cbuf[], int offset, int length) throws IOException

public int read() throws IOException

public void close() throws IOException
  • 其他方法
public boolean ready() throws IOException
public String getEncoding()

2.FileReader

本质:给定默认字符集与buffer大小的InputStreamReader

  • 构造器
public FileReader(String fileName) throws FileNotFoundException
public FileReader(File file) throws FileNotFoundException
public FileReader(FileDescriptor fd)

3.OutputStreamWriter

底层StreamEncoder

  • 构造器(必须以OutputStream为入参)
// 实际调用 StreamEncoder的构造器
public OutputStreamWriter(OutputStream out)
public OutputStreamWriter(OutputStream out, String charsetName)
public OutputStreamWriter(OutputStream out, Charset cs)
public OutputStreamWriter(OutputStream out, CharsetEncoder enc)
  • 核心方法

核心:将字符数组write到输出流

public void write(String str, int off, int len) throws IOException
public void write(char cbuf[], int off, int len) throws IOException
public void write(int c) throws IOException

public void flush() throws IOException{
    1.flushBuffer()
    2.flush输出流
}
public void close() throws IOException
  • 其他方法
void flushBuffer() throws IOException
public String getEncoding()

4.FileWriter

本质:给定默认字符集与buffer大小的OutputStreamWriter

  • 构造器
public FileWriter(String fileName) throws IOException
public FileWriter(String fileName, boolean append) throws IOException
public FileWriter(File file) throws IOException
public FileWriter(File file, boolean append) throws IOException
public FileWriter(FileDescriptor fd)

5.demo

功能1:用FileReader和FileWriter复制文本文件

注:和上述的字节流传输代码相似,只是换成用char[]传输,因此需要的话可以自行输出方便阅读的chars

    try(
                FileReader fileReader=new FileReader("D:\\fileTest\\app.properties");
                FileWriter fileWriter=new FileWriter("D:\\fileTest\\out2.properties")
        ) {
            char[] chars=new char[1024];
            int len=0;
            while ((len=fileReader.read(chars))!=-1){
                fileWriter.write(chars,0,len);
            }
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

功能2:用InputStreamReader读取properties

InputStreamReader reader=new InputStreamReader(new FileInputStream("D:\\fileTest\\app.properties"));
Properties properties=new Properties();
properties.load(reader);
properties.forEach((k,v)-> System.out.println(k+":"+v));

三、总结

本节研究了基础的文件操作类,包括字节流FileInputStream、FileOutputStream,字符流InputStreamReader及其子类FileReader,OutputStreamWriter及其子类FileWriter,注意文件字符流必须通过字节流来构造,这些类都可以实现读写文件,一般情况下我们使用字节流读写二进制文件,字符流读写文本文件(比如properties等包含中文的配置文件)。

下一节我们将探讨使用较频繁的Object流。

相关文章

网友评论

    本文标题:java.io源码解析(二)--文件操作(FileInputSt

    本文链接:https://www.haomeiwen.com/subject/idzltctx.html