File类,RandomAccessFile类,IO流,NIO流

目录

一、File类

1、基本概念

文件信息

相对路径

绝对路径

路径分隔符

2、File类的用处

3、File类的构造方法

4、File类的API

5、File类的练习

使用代码创建一个java工程目录  

二、RandomAccessFile类

1、RandomAccessFile类

2、RandomAccessFile类的实现原理

3、RandomAccessFile类的API

4、RandomAccessFile类的练习

1、复制文件

2、图片美白

三、IO流原理及分类

1、IO流

2、文件的分类

3、IO流的分类

4、InputStream和OutputStream

InputStream和OutputStream的API

5、FileInputStream和FileOutputStream

FileInputStream和FileOutputStream的API

6、练习

将0.txt和1.txt合并为一个3.txt文件

7、BufferedInputStream和BufferedOutputStream

BufferedInputStream和BufferedOutputStream的API

8、Reader和Writer

Reader和Writer的API

9、FileReader和FileWriter

FileReader和FileWriter的API

10、BufferedReader和BufferedWriter

BufferedReader和BufferedWriter的API

11、InputStreamReader和OutputStreamWriter

InputStreamReader和OutputStreamWriter的API

12、PrintStream和PrintWriter

PrintWriter的API

13、练习

下载网页 

14、总结

读写二进制文件

读写文本文件

将字节流转换成字符流

读取控制信息

打印各种格式信息

读写对象(序列化和反序列化)

序列化和反序列化

序列化和反序列化管道

四、字符编码

常见的编码表

五、transient关键字

六、Serializable接口

七、浅拷贝和深拷贝

八、NIO

一、File类

1、基本概念

文件信息

指文件名,类型,扩展名 ,修改时间等

相对路径

指相较于某个路径下,指明的路径

绝对路径

指包含盘符在内的文件及文件目录的路径

路径分隔符

路径中的每级目录之间用一个路径分隔符隔开

windows和DOS:“\”

UNIX和URL:“/”

因为Java程序支持跨平台运行,因此路径分隔符要慎用。

为了解决跨平台隐患,File类提供了一个常量:

public static final String separator:根据操作系统,动态的提供分隔符

2、File类的用处

  • File类声明在java.io包下:java.io.File
  • File类的一个对象,表示一个文件或一个文件目录
  • File类能新建、删除、重命名文件和目录,但不能对文件内容进行访问
  • File对象可以作为参数传递给流的构造器

3、File类的构造方法

  • public File(String pathname) :以pathname为路径创建File对象,可以是绝对路径或者相对路径,如果 pathname是相对路径,则默认的当前路径在系统属性user.dir中存储
  • public File(String parent,String child) :以parent为父路径,child为子路径创建File对象
  • public File(File parent,String child) :根据一个父File对象和子文件路径创建File对象

4、File类的API

  • File(String pathname):根据路径的名字读取一个文件或一个文件目录信息,并在内存中创建一个File对象
  • String getName():获取名称
  • String getPath():获取路径
  • String getAbsolutePath():获取绝对路径
  • File getParentFile():获取上一级目录
  • String getParent():获取上层文件目录的路径,若无,返回null
  • long length():获取文件的长度即字节数,不能获取目录的长度。如果文件内容为空,或者文件不存在,返回0
  • long lastModified():获取最后一次修改的时间,毫秒值
  • boolean exists():判断当前文件或目录是否存在
  • boolean isFile():判断是否是文件
  • boolean isDirectory():判断是否是目录
  • boolean createNewFile():用于创建一个空文件,如果文件存在,就不会创建文件
  • boolean mkdir():用于创建目录,如果目录已经存在返回false ,只能创建最后一级目录
  • boolean mkdirs():用于创建多级目录,就是一个完整的目录树
  • boolean delete():用于删除文件或目录,只能删除文件或空目录
  • String[] list():获取指定目录下的所有文件或文件目录的名称数组
  • File[] listFiles():获取指定目录下的所有文件或文件目录的File数组
  • File[] listFiles(FileFilter filter):获取根据指定过滤信息找到的满足条件的File数组

5、File类的练习

使用代码创建一个java工程目录  

|-.settings目录 
|-.classpath文件
|-.project文件
|-src目录
|-bin目录

import java.io.File;
import java.io.IOException;

public class FileDemo {

    public static void main(String[] args) throws IOException {

        File f1 = new File("D:/javahomework");
        Boolean isMk = f1.mkdirs();
        System.out.println("主目录是否被创建:"+isMk);
        File f2 = new File("D:/javahomework/settings");
        File f3 = new File("D:/javahomework/.classpath");
        File f4 = new File("D:/javahomework/.project");
        File f5 = new File("D:/javahomework/src");
        File f6 = new File("D:/javahomework/bin");
        Boolean isMk2 = f2.mkdirs();
        Boolean isCreate3 = f3.createNewFile();
        Boolean isCreate4 = f4.createNewFile();
        Boolean isMk5 = f5.mkdirs();
        Boolean isMk6 = f6.mkdirs();
        System.out.println("子目录是否被创建:"+isMk2);
        System.out.println("文件classpath是否被创建:"+isCreate3);
        System.out.println("文件project是否被创建:"+isCreate4);
        System.out.println("子目录是否被创建:"+isMk5);
        System.out.println("子目录是否被创建:"+isMk6);
  }
}

二、RandomAccessFile类

1、RandomAccessFile类

RandomAccessFile类声明在java.io包下:java.io.RandomAccessFile。

2、RandomAccessFile类的实现原理

在文件内部使用一个游标指针,这个指针可以随意指向文件的任何位置,然后通过指针访问文件内容。

3、RandomAccessFile类的API

  • RandomAccessFile(File file, String mode):File:文件对象信息,String mode:r读 w:写 rw:读写
  • long length():文件的长度
  • int read():从文件中读取一个字节的数据,返回值为int类型,读取的内容为一个字节,把字节无符号扩展为int
  • void write(int b):将一个字节的数据写入到文件,只会取低八位保存到文件中
  • int read(byte[] b):将读取的数据保存到数组中,并返回读取数据长度;
  • void write(byte[] b,int off,int len):将数组中的数据 从 off开始,把长度为len的数据写入到文件
  • byte[] b:读取的数据,int off:从off下标开始,int len:读取数据的长度,如果到了文件末尾返回-1,游标都会后移一个位置
  • void close():关闭文件
  • long getFilePointer():获取指针的位置
  • void seek(long pos):设置指针的位置

4、RandomAccessFile类的练习

1、复制文件

import java.io.File;
import java.io.IOException;
import java.io.RandomAccessFile;

public class RandomAccessFileDome {
    public static void main(String[] args) throws IOException{
        copy();
    }
    private static void copy() throws IOException{
        File f1 = new File("D:/0/0.txt");
        RandomAccessFile f2 = new RandomAccessFile(f1,"rw");

        File f3 = new File("D:/javahomework/0.text");
        RandomAccessFile f4 = new RandomAccessFile(f3,"rw");

        if(!f3.exists()){
            f3.createNewFile();
        }

        while (true){
            int data = f2.read();
            if(data == -1){
                break;
            }
            f4.write(data);
        }
        f2.close();
        f4.close();
    }
}

2、图片美白

import java.io.File;
import java.io.IOException;
import java.io.RandomAccessFile;

public class PicDemo {
    public static void main(String[] args) throws IOException {
        File f = new File("D:/javahomework/1.bmp");
        RandomAccessFile raf = new RandomAccessFile(f,"rw");
        raf.seek(54);
        while (true){
            int data = raf.read();
            long pointer = raf.getFilePointer();
            if(data == -1)break;
            data+=100;
            if(data>255){
                data = 255;
            }
            raf.seek(pointer-1);
            raf.write(data);
        }
        raf.close();
    }
}

三、IO流原理及分类

1、IO流

  • I/O是Input/Output的缩写
  • IO流用于处理设备之间的数据传输
  • Java程序中,对数据的输入输出操作以“流(stream)”的方式进行
  • IO流原理:以内存或内存中存在应用程序实例(进程)为参照物,向其输入数据(Input)或输出数据(Output)
  • Input(输入):读取外部数据(磁盘,光盘,网络等)到程序(内存)中
  • Output(输出):将程序(内存)中的数据输出到磁盘,光盘,网络等存储设备中
  • java.io包下提供各种“流”类和接口,用以获取不同种类的数据,并通过标准的方法对数据进行输入或输出

2、文件的分类

  • 文本文件:字符(char),.txt,.java,.html,.xml
  • 二进制文件:二进制(byte),.docx,视频,音频,图片

3、IO流的分类

  • 按操作的数据单位分:字节流(byte 8bit),字符流(char 16bit)
  • 按流的流向分:输入流,输出流
  • 按流的角色分:节点流(能直接和介质相连的IO流,介质:文件、网络等),处理流(只能和IO流连接的IO流)
抽象基类      字节流 字符流
输入流 InputStream Reader
输出流 OutputStream Writer
  • 字节流:读取的最小单位是byte
  • 字符流:读取的最小单位是char
  • 注:Java的IO流虽然共涉及四十多个类,但实际上非常规则,因为四十多个类都是四个抽象基类派生的,由这四个抽象基类派生的子类都是以其父类名作为子类名的后缀
抽象基类 节点流(文件流) 缓冲流(处理流的一种)
InputStream FileInputStream BufferedInputStream
OutputStream FileOutputStream BufferedOutputStream
Reader FileReader BufferedReader
Writer FileWriter BufferedWriter

File类,RandomAccessFile类,IO流,NIO流

4、InputStream和OutputStream

  • 最小单位:字节(byte)
  • 字节流的抽象基类

InputStream和OutputStream的API

  • int read():读取一个字节的数据,返回一个无符号的int
  • int read(byte[] b):将读取的数据存储到数组中,并且返回读取数据数据的长度,如果到了文件末尾,返回-1
  • void close():关闭IO流
  • void write(byte[] b, int off, int len):将数组中从off开始,长度为len的数据写入到文件中
  • void flush():将数据刷出

5、FileInputStream和FileOutputStream

  • 文件字节流; 
  • 节点流

FileInputStream和FileOutputStream的API

  • FileInputStream(File file):File file:文件对象
  • FileInputStream(String name):String name:文件路径
  • FileOutputStream(File file):File file:文件对象
  • FileOutputStream(File file, boolean append):File file:文件对象;boolean:true:在原有的文件内容基础上追加;false:将源文件的内容给覆盖
  • FileOutputStream(String name):String name:文件路径
  • FileOutputStream(String name, boolean append):String name:文件路径;boolean:true:在原有的文件内容基础上追加;false:将源文件的内容给覆盖

6、练习

将0.txt和1.txt合并为一个3.txt文件

import java.io.*;

public class Merge {

    public static void main(String[] args) throws IOException {
        mergeByte();
    }

    private static void mergeByte() throws IOException{
        BufferedInputStream bis0 = new BufferedInputStream(new FileInputStream(new File("D:/0/0.txt")));
        BufferedInputStream bis1 = new BufferedInputStream(new FileInputStream(new File("D:/0/1.txt")));
        BufferedOutputStream bos3 = new BufferedOutputStream(new FileOutputStream(new File("D:/0/3.txt"),true));

        byte[] data = new byte[1024];

        while (true){
            int len = bis0.read(data);
            if(len==-1)break;
            bos3.write(data,0,len);
        }
        bis0.close();

        while (true){
            int len = bis1.read(data);
            if(len==-1)break;
            bos3.write(data,0,len);
        }
        bis1.close();
        bos3.close();
    }
}

7、BufferedInputStream和BufferedOutputStream

  • 缓冲流,内部有缓存,缓冲区大小,默认8k
  • 处理流

BufferedInputStream和BufferedOutputStream的API

  • BufferedInputStream(InputStream in):InputStream in:字节节点流或字节处理流
  • BufferedInputStream(InputStream in, int size):InputStream in:字节节点流或字节处理流;int size:可以手动设置缓冲区大小,默认:8k
  • BufferedOutputStream(OutputStream out):OutputStream out:字节节点流或字节处理流
  • BufferedOutputStream(OutputStream out, int size):OutputStream out:字节节点流或字节处理流;int size:可以手动设置缓冲区大小,默认:8k

8、Reader和Writer

  • 最小单位:字符(char)
  • 字符流的抽象基类

Reader和Writer的API

  • int read():读取数据是一个字符,返回值也是经过了无符号扩展
  • int read(char[] cbuf):读取的数据保存在char数组中,并且返回读取字符的长度,如果到达文件末尾返回-1
  • void close():关闭管道流的方法
  • void write(int c):写入一个字符,写数据的时候将高16位去掉
  • void write(char[] cbuf, int off, int len):将数组中从off开始,len长度的字符写入到文件中
  • void write(String str):将字符串写入到文件中
  • Writer append(char c)将字符追加到文件中
  • void flush():将数据刷出

9、FileReader和FileWriter

  • 文件字符流
  • 节点流

FileReader和FileWriter的API

  • FileReader(File file):File file:文件对象
  • FileReader(String fileName):String fileName:文件的路径
  • FileWriter(File file):File file:文件对象
  • FileWriter(File file, boolean append):File file:文件对象;boolean:true:在原有的文件内容基础上追加,false:将源文件的内容给覆盖
  • FileWriter(String fileName):String fileName:文件的路径
  • FileWriter(String fileName, boolean append):String fileName:文件的路径;boolean:true在原有的文件内容基础上追加,false将源文件的内容给覆盖

10、BufferedReader和BufferedWriter

  • 缓冲流,内部有缓存,缓冲区大小,默认16k
  • 处理流

BufferedReader和BufferedWriter的API

  • BufferedReader(Reader in):Reader in:字符节点流或字符处理流
  • String readLine():读取一个文本行,行尾有一个\n,返回值null
  • BufferedWriter(Writer out):Writer out:字符节点流或字符处理流
  • BufferedWriter(Writer out, int sz):Writer out:字符节点流或字符处理流;int sz:可以手动设置缓冲区大小,默认:16k
  • void newLine():写入一个行分隔符

11、InputStreamReader和OutputStreamWriter

  • 转换流,将字节流转换成字符流  (文本文件)
  • 处理流

InputStreamReader和OutputStreamWriter的API

  • InputStreamReader(InputStream in):InputStream in:节点流或处理流
  • InputStreamReader(InputStream in, String charsetName):InputStream in:节点流或处理流;String charsetName:字符集 ,默认OS字符集
  • OutputStreamWriter(OutputStream out):OutputStream out:节点流或处理流
  • OutputStreamWriter(OutputStream out, String charsetName):OutputStream out:节点流或处理流;String charsetName:字符集 ,默认OS字符集
  • 常用字符集:utf-8,GBK,GB2312,ISO8859-1

File类,RandomAccessFile类,IO流,NIO流

 

12、PrintStream和PrintWriter

  • 打印流,既是节点流又是处理流
  • 实现将基本数据类型的数据格式转化为字符串输出
  • 提供了一系列重载的print()和println()方法,用于多种数据类型的输出
  • PrintStream和PrintWriter的输出不会抛出IOException异常
  • PrintStream和PrintWriter有自动flush功能
  • PrintStream打印的所有字符都使用平台的默认字符编码转换为字节,在需要写入字符而不是写入字节的情况下,应该使用 PrintWriter 类
  • System.out返回的是PrintStream的实例

PrintWriter的API

  • PrintWriter(File file):File file:文件对象
  • PrintWriter(String fileName):String fileName:文件路径
  • PrintWriter(OutputStream out):OutputStream out:字节输出流
  • PrintWriter(Writer out):Writer out:字符输出流
  • void print(String s):String s:输出字符串
  • void println(String x):String x:输出字符串并且换行
  • void print(Object obj):Object obj:输出对象       

13、练习

下载网页 

URL url = new URL("http://www.baidu.com");
InputStream in =url.openStream();

import java.io.*;
import java.net.URL;

public class Nett {

    public static void main(String[] args) throws IOException {
        myNett();
    }

    private static void myNett() throws IOException{
        BufferedReader br1 = new BufferedReader(new InputStreamReader(
                                 new URL("https://www.baidu.com/").openStream(),"utf-8"));
        BufferedWriter bw1 = new BufferedWriter(new OutputStreamWriter(new FileOutputStream("D:/0/net.txt")));

        char[] buf = new char[1024];

        while(true){
            int len = br1.read(buf);
            if(len == -1)break;
            String str = new String(buf,0,len);
            bw1.write(str);
        }
        br1.close();
        bw1.close();
    }
}

14、总结

读写二进制文件

  • new BufferedInputStream(new FileInputStream())
  • new BufferedOutputStream(new FileOutputStream())

读写文本文件

  • new BufferedReader(new FileReader())
  • new BufferedWriter(new FileWriter())

将字节流转换成字符流

  • new BufferedReader(new InputStreamReader(new FileInputStream(),"utf-8"))
  • new BufferedWriter(new OutputStreamWriter(new FileOutputStream(),"utf-8"))

读取控制信息

  • new Scanner(System.in)
  • new BufferedInputStream(System.in)

打印各种格式信息

  • new PrintWriter(new BufferedWriter(new FileWriter()))

读写对象(序列化和反序列化)

  • new ObjectInputStream(new BufferedInputStream(new FileInputStream()))
  • new ObjectOutputStream(new BufferdOutputStream(new FileOutputStream()))

序列化和反序列化

  • 序列化:将内存中的对象转换成二进制的过程
  • 反序列化:将二进制数据转换成内存中的对象

序列化和反序列化管道

  • new ObjectInputStream(new BufferedInputStream(new FileInputStream()))
  • new ObjectOutputStream(new BufferdOutputStream(new FileOutputStream()))   

四、字符编码

常见的编码表

  • ASCII:美国标准信息交换码,用一个字节的7位可以表示
  • ISO8859-1:拉丁码表,欧洲码表,用一个字节的8位表示
  • GB2312:中国的中文编码表,最多两个字节编码所有字符
  • GBK:中国的中文编码表升级,融合了更多的中文文字符号,最多两个字节编码
  • Unicode:国际标准码,融合了目前人类使用的所有字符,为每个字符分配唯一的 字符码,所有的文字都用两个字节来表示
  • UTF-8:变长的编码方式,可用1~4个字节来表示一个字符

五、transient关键字

被关键字修饰的字段不参与序列化(密码等敏感字段,在序列化时,不允许写到文件,字段前加transient关键字进行修饰)

六、Serializable接口

  • 标识接口
  • 要序化的对象必须实现Serializable接口,以启动序列化的功能
  • 静态是不能被序列化的(序列化只能对堆中的对象进行序列化,不能对方法区中的对象进行序列化)

七、浅拷贝和深拷贝

  • 深拷贝:通过序列化和反序列实现对象完全拷贝
  • 浅拷贝:JVM默认是的一种拷贝方式

八、NIO

早期的Java只提供了一个File类来访问文件系统,但File类的功能比较有限,提供的方法性能也不高,大多数方法在出错时仅返回失败,并不会提供异常信息。

NIO为了弥补不足,引入了Path接口,代表一个平台无关的平台路径,描述了目录结构中文件的位置。

Path可以看成是File类的升级,引用的资源可以不存在。

IO:

import java.io.File;

File file = new File("01.html");

NIO:

import java.nio.file.Path;

import java.nio.file.Paths;

Path path = Paths.get("01.html");

上一篇:Java-Work9-文件输入与输出(4)


下一篇:java io 之RandomAccessFile类