【Java之文件操作与IO】重要题型讲解

这篇博客通过三个实战例子详细讲解了Java中文件操作和IO流的运用,包括删除指定字符的文件、复制文件以及全文检索。首先,展示了如何遍历目录并删除包含特定字符的文件,接着演示了如何实现文件的复制,包括目标路径检查和实际复制过程。最后,实现了一个全文检索功能,搜索指定目录下文件名或内容包含特定关键词的文件。整个过程涉及递归遍历、文件读写等关键知识点。
摘要由CSDN通过智能技术生成

文件操作及IO流算是Java中相对之前多线程部分简单一点的内容了,但需要记忆的内容和一些细节也是蛮多的,下面博主通过两个题带大家巩固巩固这部分内容吧!

在这里插入图片描述

补充

  1. 绝对路径:绝对路径是描述文件位置的完整路径,通常是从盘符开始的路径,由一系列连续的目录组成,中间用斜线分隔,直到要指定的目录或文件,路径中的最后一个名称即为要指向的目录或文件。
    例如:C:\windows\system32\cmd.exe
  2. 相对路径:指由这个文件所在的路径引起的跟其它文件(或文件夹)的路径关系
    例如:..\..\windows\system32\cmd.exe
    注意:..\代表上级目录,.\代表当前目录

一. 删除指定字符的文件

1. 题目描述

制定一个目录,要求扫描一个目录,找到文件名中包含了指定字符的文件,并提示用户是否要删除这个文件,根据用户输入决定是否要删除这个文件

2. 具体思路

由于目录中包含了其他目录(文件),因此需要通过递归的方式,来获取到里面的内容

3. 实现过程

import java.io.File;
import java.io.IOException;
import java.util.*;

public class Test {
    public static void main(String[] args) throws IOException {
        // 1.让用户指定一个待扫描的根目录和要查询的关键词
        System.out.println("请输入要扫描的根目录(绝对路径): ");
        Scanner scanner = new Scanner(System.in);
        String root = scanner.next();
        File rootDir = new File(root);//通过file这个实例表示具体的文件或路径
        if (!rootDir.isDirectory()) {//判断是否为目录
            System.out.println("您输入的路径错误! 程序直接退出!");
            return;
        }
        System.out.println("请输入要查找的文件名中包含的关键词: ");
        String token = scanner.next();
        // 2.通过递归的方式遍历目录
        // result表示递归遍历的结果,包含着所有带有token关键词的文件名
        List<File> result = new ArrayList<>();
        scanDir(rootDir, token, result);
        // 3.遍历 result,问用户是否要删除该文件,根据用户的输入决定是否删除
        for (File f : result) {
            System.out.println(f.getCanonicalPath() + " 是否要删除? (Y/N)");
            String input = scanner.next();
            if (input.equals("Y")) {
                f.delete();
            }
        }
    }
    //递归过程
    private static void scanDir(File rootDir, String token, List<File> result) throws IOException {
        // list返回的是一个文件名(String), 使用 listFiles 直接得到的是 File 对象, 使用起来更方便
        File[] files = rootDir.listFiles();
        if (files == null || files.length == 0) {
            // 当前的目录是一个空的目录
            return;
        }
        for (File f : files) {
            if (f.isDirectory()) {
                // 如果当前的文件是一个目录, 就递归的进行查找
                scanDir(f, token, result);
            } else {
                // 如果当前文件是一个普通的文件, 就判定这个文件是否包含了待查找的关键词
                if (f.getName().contains(token)) {
                    result.add(f.getCanonicalFile());
                }
            }
        }
    }
}

运行结果展示:
在这里插入图片描述

二. 复制文件

1. 题目描述

设计一个程序,要求让用户输入一个文件的路径(绝对路径),要求这个文件是一个普通的文件(不是目录),然后再指定一个要复制过去的目标目录。通过程序,把这个文件进行复制

2. 具体思路

主要考察复制操作:打开待复制的文件,读取出每个字节, 然后再把这些字节给写入到目标的文件中,同时需要注意目标文件的存在情况和目标文件的父目录存在情况

3. 实现过程

import java.io.*;
import java.util.*;

public class Test {
    public static void main(String[] args) throws IOException {
        Scanner scanner = new Scanner(System.in);
        System.out.println("请输入要复制的文件: (绝对路径)");
        String srcPath = scanner.next();
        File srcFile = new File(srcPath);
        if (!srcFile.isFile()) {
            System.out.println("文件路径错误! 程序直接退出");
            return;
        }
        System.out.println("请输入要复制到的目标路径: (绝对路径)");
        String destPath = scanner.next();
        // 要求这个destFile必须不能存在,否则将会覆盖
        File destFile = new File(destPath);
        if (destFile.exists()) {
            System.out.println("目标文件的路径已经存在! 程序直接退出!");
            return;
        }
        if (!destFile.getParentFile().exists()) {
            // 父级目录不存在, 也提示一个报错, 也可以不存在就创建出来. 使用 mkdirs 就能创建.
            System.out.println("目标文件的父目录不存在! 程序直接退出!");
            return;
        }
        // 具体进行复制操作.
        try (InputStream inputStream = new FileInputStream(srcFile);
             OutputStream outputStream = new FileOutputStream(destFile)) {
            // 从 inputStream中按照字节来读, 然后把结果写入到 outputStream 中
            while (true) {
                byte[] buffer = new byte[1024];
                int len = inputStream.read(buffer);
                if (len == -1) {
                    break;
                }
                outputStream.write(buffer, 0, len);
            }
            // 如果这里不加 flush, 触发 close 操作, 也会自动刷新缓冲区.
            outputStream.flush();
        } catch (IOException e) {
            e.printStackTrace();
        }
        System.out.println("复制完成!");
    }
}

运行结果展示:
在这里插入图片描述

三. 全文检索

1. 题目描述

设计一个程序,扫描指定目录,并找到名称或者内容中包含指定字符的所有普通文件。

2. 具体思路

  1. 让用户输入一个待搜索的路径
  2. 接着让用户输入一个查询词,表示要搜索的结果中包含这个词
  3. 遍历目录以及文件进行匹配(递归)

3. 实现过程

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;

public class Test {
    public static void main(String[] args) throws IOException {
        Scanner scanner = new Scanner(System.in);
        // 1.用户输入一个待搜索的路径
        System.out.println("请输入要扫描的根目录: ");
        String rootDir = scanner.next();
        File rootFile = new File(rootDir);
        if (!rootFile.isDirectory()) {
            System.out.println("该目录不存在或者不是文件! 直接退出. ");
            return;
        }
        // 2.再让用户输入一个查询词, 表示要搜索的结果中要包含这个词.
        System.out.println("请输入要查询的词: ");
        String query = scanner.next();
        // 3.遍历目录以及文件, 进行匹配
        List<File> results = new ArrayList<>();
        scanDirWithContent(rootFile, query, results);
        // 4. 打印出结果
        for (File f : results) {
            System.out.println(f.getCanonicalPath());
        }
    }

    private static void scanDirWithContent(File rootFile, String query, List<File> results) {
        File[] files = rootFile.listFiles();
        if (files == null || files.length == 0) {
            // 若是空的目录, 直接返回
            return;
        }
        for (File f : files) {
            if (f.isDirectory()) {
                scanDirWithContent(f, query, results);
            } else {
                if (f.getName().contains(query)) {
                    // 检查文件名称中是否包含
                    results.add(f);
                } else if (isContentContains(f, query)) {
                    // 检查文件内容中是否包含
                    results.add(f);
                }
            }
        }
    }

    private static boolean isContentContains(File f, String query) {
        // 打开 f 这个文件, 依次取出每一行结果, 去和query来进行一个indexOf
        StringBuilder stringBuilder = new StringBuilder();
        try (InputStream inputStream = new FileInputStream(f)) {
            Scanner scanner = new Scanner(inputStream, "UTF-8");
            while (scanner.hasNextLine()) {
                String line = scanner.nextLine();
                stringBuilder.append(line + "\n");
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        // 只要结果不等于 -1, 就说明查到了.
        return stringBuilder.indexOf(query) != -1;
    }
}

运行结果展示:在这里插入图片描述

评论 11
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

春风~十一载

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值