Fork me on GitHub

IO 之 File 类

  1. 位于 java.io 包
  2. 用来将文件或者文件夹封装成对象
  3. 方便对文件和文件夹的属性信息进行操作
  4. File 对象可以作为参数传递给流的构造函数

构造函数

// 可以将一个已存在的, 或者不存在的文件或者目录封装成 File 对象
    File f1 = new File("c:\\a.txt");

    // 第二种方式
    File f2 = new File("c:\\","a.txt");

    // 第三种方式
    File f = new File("c:\\");
    File f3 = new File(f,"a.txt");

字段摘要

// 名称分隔符
static char separatorChar : 此字段为系统属性 file.separator 值的第一个字符.
                            在 UNIX 系统上, 此字段值为 '/'; 在 Windows 系统上, 它为 '\\'
static String separator

// 路径分隔符
static char pathSeparatorChar : 此字段为系统属性 path.separator 值的第一个字符.

static String pathSeparator

常见方法

// 1. 获取
        1.1 获取文件名称:  file.getName();
        1.2 获取文件绝对路径:  file.getAbsolutePath();
        1.3 获取文件相对路径:  file.getPath();
        1.4 获取文件大小:  long file.length();
        1.5 获取文件修改时间:  long file.lastModified();

// 2. 创建与删除
        返回值为 boolean, 没有参数.
        2.1 创建与删除文件
            File file = new File("a.js");  // 将文件封装成对象

            // 对文件的创建和删除
            boolean b = file.createNewFile(); // 与输出流方式不一样, 如果文件不存在, 则创建;
                                              // 如果文件存在, 则不创建
            boolean b = file.delete();

            void deleteOnExit(); // 在虚拟机退出时, 删除文件或文件夹

        2.2 创建与删除文件夹
            // 将文件夹封装成对象
            File dir = new File("abc");
            boolean b = dir.mkdir();  // 创建单级目录

            File dir = new File("abc\\e\\f");
            boolean b = dir.mkdirs(); // 创建多级目录

            boolean b = dir.delete(); // 目录内有内容, 则无法删除

// 3. 判断
        File file = new File("a.js");
        // 最好先判断文件是否存在
        boolean b = f.exists();
        // 判断是否是个文件
        boolean b = f.isFile();
        // 判断是否是个文件夹
        boolean b = f.isDirectory();

// 4. 重命名
        File f1 = new File("c:\\0.mp3");
        File f2 = new File("d:\\9.mp3");
        // 如果重命名之后的文件与之前的文件不在同一个文件夹下, 会发生剪切
        boolean b = f1.renameTo(f2);  

// 其他
     1. // 获取所有盘符, 静态方法,可以直接类名调用
        File[] files = File.listRoots();

        File file = new File("d:\\");
        // 获取某个盘符空闲空间
        file.getFreeSpace();
        // 获取某个盘符总空间
        file.getTotalSpace();
        // 获取某个盘符已用空间
        file.getUsableSpace();

     // 2. 获取当前目录下的文件以及文件夹的名称, 包含系统隐藏文件
                File f = new File("C:\\");
                String[] names = f.list();
                for(String name:names){
                    System.out.println(name);
                }

      // 注意: 调用 list 方法的 File 对象中封装的必须是目录(文件夹),
             // 否则, 会发生 NullPointerException 异常
              // 如果访问的是系统级目录, 也会发生空指针异常.
              // 如果目录存在,但是没有内容, 会返回一个数组, 但是长度为 0.

    // 3. 获取当前目录下所有文件对象
            File dir = new File("c:\\");
            File[] files = dir.listFiles();

过滤器

  1. 文件名过滤:
    • FilenameFileter 接口
    • 只有一个方法 boolean accept(File dir, String name);
  2. 文件过滤
    • FileFilter 接口
// 需求: 获取某一个盘符下的 .java 文件

    public static void listDemo(){
        File dir = new File("c:\\");

        //  String[] names = dir.list();   返回 c 盘下的所有文件和目录
        Strig[] names = dir.list(new FilterByJava());
    }

    // 创建过滤器对象
    public class FilterByJava implements FilenameFilter{

        public boolean accept(File dir, String name){  // name 为目录下所有文件的名称

            return name.endsWith(".java");
        }
    }

// 需求二: 获取某一盘符下不是隐藏的文件
    public static void listDemo_1(){
        File dir = new File("c:\\");

        File[] files = dir.listFile(new FilterByHidden());
    }

    // 创建过滤文件对象
    public class FilterByHidden implements FileFilter{

        public boolean accept(File pathname){

            return !pathname.isHidden();
        }
    }

深度遍历文件夹

// 需求: 对指定目录进行所有内容的列出(包含子目录中的内容)
      // 也可以理解为深度遍历

  public static void main(String[] args){

    File dir = new File("e:\\demodir");

    listAll(dir);
}

  public static void listAll(File dir){

    // 输出文件夹名称
    System.out.println("dir: "+dir.getName());

    // 获取指定目录下, 当前的所有文件夹或者文件对象
    File[] files = dir.listFiles();

    for(int x=0; x<files.length; x++){

        if(files[i].isDirectory){
            listAll(files[x]);
        } else {
            System.out.println(files[x].getName());
        }
    }
    }

// 升级版,显示为目录层级格式

    public static void main(String[] args){

        File dir = new File("e:\\demodir");

        listAll(dir,0);
    }

    public static void listAll(File dir, int level){

        System.out.println(getSpace(level)+dir.getName());

        level++;
        File files = dir.listFiles();

        for(int x=0; x<files.length; x++){

            if(files[x].isDirectory()){
                listAll(files[x],level);
            }else{
                System.out.println(getSpace(level)+files[x].getName());
            }
        }
    }

    public static String getSpace(int level){

        StringBuilder sb = new StringBuilder();

        sb.append("|--")
        for(int x=0; x<level; x++){
            sb.insert(0,"|   ");  // 在 0 位置插入
        }

        return sb.toString();
    }

递归

  1. 函数自身直接或者间接调用了自身
  2. 注意:
    • 递归一定要明确条件, 否则容易栈溢出
    • 注意递归的次数. 次数过多, 也会导致栈溢出
// 输入一个数, 获取从 1 到这个数的和
// 例如 输入3, 获取 1~3 的和

public static int getSum(int num){
    if(num == 1)
        return 1;

    return num+getSum(num-1);
}

// 综合练习: 获取指定目录下, 指定扩展名的文件(包含子目录中的文件)
          // 将这些文件的绝对路径写入到一个文本文件中
          // 简单说, 就是建立一个指定扩展名的文件列表

      /*
       * 思路:
       *    1. 必须对文件夹进行深度遍历
       *    2. 要在遍历的过程中进行过滤, 将符合条件的内容都存储到容器中
       *    3. 对容器中的内容进行遍历并将绝对路径写入到文件中
       */

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

            File dir = new File("e:\\java");

            // 匿名内部类
            FilenameFilter filter = new FilenameFilter(){
                public boolean accept(File dir, String name){
                    return name.endsWith(".java");
                }
            };

            List<File> list = new ArrayList<File>();

            getFiles(dir,filter,list);

            File destFile = new File(dir,"javalist.txt");
            write2File(list,destFile);
        }

        // 将符合条件的内容存储到容器中
        public static void getFiles(File dir, FilenameFileter filter, List<File> list){

            File[] files = dir.listFiles();

            for(File file : files){
                if(file.isDirectory){
                    // 递归, 进行深度遍历
                    getFiles(file, filter, list);
                } else {
                    // 对遍历到的文件进行过滤器的过滤, 将符合条件的 File 对象, 存储到 List 集合中
                    if(filter.accept(dir,file.getName())){
                        list.add(file);
                    }
                }
            }
        }

        public static void write2File(List<File> list, File destFile) throws IOException{

            BufferedWriter bufw = null;
            try{
                bufw = new BufferedWriter(new FileWriter(destFile));

                for(File file:list){
                    bufw.write(file.getAbsolutePath()); // 按写入字符串的方式
                    bufw.newLine();
                    bufw.flush();  // 不要忘记刷新
                }                
            } finally {
                if(bufw!=null)
                    try{
                        bufw.close();
                    } catch (IOException e){
                        throw new RuntimeException("关闭失败");
                    }
            }
    }

参考资料

posted @ 2017-09-13 16:51  小a的软件思考  阅读(156)  评论(0编辑  收藏  举报