🌷 Java 中操作文件
Java 中通过 java.io.File 类来对一个文件(包括目录)进行抽象的描述。注意,有 File 对象,并不代表真实存在该文件。
io(输入输出):输入输出是以内存为参照物的,输入是从外部输入到内存,输出是把内存的数据输出到外部(磁盘,网卡等)
File属性
File构造方法
File方法
public class Demo01_File {
public static void main(String[] args) throws IOException {
//需要转义
//指定绝对路径
File file = new File("D:\\ui\\java\\so.png");
System.out.println( "返回 File 对象的父目录文件路径: " + file.getParent());
System.out.println("返回 FIle 对象的纯文件名称: " + file.getName());
System.out.println("返回 File 对象的文件路径: " + file.getPath());
System.out.println("返回 File 对象的绝对路径: " + file.getAbsolutePath());
System.out.println("返回 File 对象的修饰过的绝对路径: " + file.getCanonicalPath());
//这是Java层面的对象,并不必须要在系统中真实存在
File file1 = new File("D:\\ui\\java\\so1.png");
System.out.println(file1);
System.out.println(file.getParent());
}
}
public class Demo02_File {
public static void main(String[] args) throws IOException {
//需要转义
//指定相对路径
File file = new File(".\\so.png");
System.out.println( "返回 File 对象的父目录文件路径: " + file.getParent());
System.out.println("返回 FIle 对象的纯文件名称: " + file.getName());
System.out.println("返回 File 对象的文件路径: " + file.getPath());
System.out.println("返回 File 对象的绝对路径: " + file.getAbsolutePath());
System.out.println("返回 File 对象的修饰过的绝对路径: " + file.getCanonicalPath());
}
}
//普通文件的创建
public class Demo03_Create {
public static void main(String[] args) throws IOException {
File file = new File("./hello-world.txt"); // 要求该文件不存在,才能看到相同的现象
System.out.println("判断 File 对象描述的文件是否真实存在: " + file.exists());
System.out.println("判断 File 对象代表的文件是否是一个目录: " + file.isDirectory());
System.out.println("判断 File 对象代表的文件是否是一个普通文件: " + file.isFile());
//创建文件
System.out.println( "根据 File 对象,自动创建一个空文件。成功创建后返回 true: " + file.createNewFile());
System.out.println(file.exists());
System.out.println(file.isDirectory());
System.out.println(file.isFile());
System.out.println("文件存在,返回false: " + file.createNewFile());
}
}
//普通文件的删除
public class Demo04_Delete {
public static void main(String[] args) throws IOException {
File file = new File("some-file.txt");
System.out.println(file.exists());
System.out.println(file.createNewFile());
System.out.println(file.exists());
//删除文件
System.out.println("根据 File 对象,删除该文件。成功删除后返回 true: " + file.delete());
//根据 File 对象,标注文件将被删除,删除动作会到JVM 运行结束时才会进行
System.out.println(file.exists());
}
}
public class Demo05_List {
public static void main(String[] args) {
File file = new File("./src/main/java/org/file_IO_Learn");
//返回 File 对象代表的目录下的所有文件名
String[] files = file.list();
for (int i = 0; i < files.length; i++) {
System.out.println(files[i]);//Demo01_File.java
}
}
}
public class Demo06_listFiles {
public static void main(String[] args) {
File file = new File("./src/main/java/org/file_IO_Learn");
//返回 File 对象代表的目录下的所有文件,以 File 对象表示
File[] files = file.listFiles();
for (int i = 0; i < files.length; i++) {
System.out.println(files[i]);//.\src\main\java\org\file_IO_Learn\Demo01_File.java
}
}
}
public class Demo06_mkdir {
public static void main(String[] args) {
//创建 File 对象代表的目录,
File file = new File("./src/main/java/org//temp");
// 创建单个目录,当目录不存在时才会创建成功
boolean result = file.mkdir();
if (result) {
System.out.println("创建成功");
} else {
System.out.println("创建失败");
}
}
}
public class Demo07_mkdirs {
public static void main(String[] args) {
File file = new File("./src/main/java/org/temp/a/b/d");
// 创建 File 对象代表的目录,如果必要,会创建中间目录(多层目录)
System.out.println(file.mkdirs());
}
}
public class Demo08_renameTo {
public static void main(String[] args) {
// 进行文件改名,也可以视为我们平时的剪切、粘贴操作
//文件名后缀也要写,也可以时目录
File file = new File("./hello-world.txt");
File file1 = new File("./haha.txt");
System.out.println(file.renameTo(file1));
}
}
public class Demo09_ReadAndWirte {
public static void main(String[] args) {
File file = new File("D:\\JavaUltimate\\code\\javaee_code\\haha.txt");
// 是否可写
System.out.println(file.canWrite());
// 是否可读
System.out.println(file.canRead());
}
}
🌷 文件内容的读写 —— 数据流
用完一定要关闭close()
⭐️ InputStream 概述
方法
说明
InputStream 只是一个抽象类,要使用还需要具体的实现类。关于 InputStream 的实现类有很多,基本可以认为不同的输入设备都可以对应一个 InputStream 类,我们现在只关心从文件中读取,所以使用 FileInputStream
⭐️ FileInputStream 概述
构造方法
public class Demo01_inputStream_Read01 {
public static void main(String[] args) throws IOException {
File file = new File("./haha.txt");
InputStream inputStream = new FileInputStream(file);
//读取一个字节的数据,返回 -1 代表已经完全读完了
// 读取文件内容
while (true) {
int read = inputStream.read();
// 是否读完
if (read == -1) {
break;
}
System.out.println(read);
}
// 关闭
inputStream.close();
}
}
public class Demo02_inputStream_Read02 {
public static void main(String[] args) throws IOException {
File file = new File("./haha.txt");
// 创建一个输入流
InputStream inputStream = new FileInputStream(file);
// 定义一个数组用来保存读取到的数据
byte[] bytes = new byte[1024];
// 读取文件内容
while (true) {
// 读到的数据会被填充到bytes数据中,返回读取数据的长度
int len = inputStream.read(bytes);
// 判断是否读完
if (len == -1) {
break;
}
// 打印读到的内容
//byte只能存储-128 ~ 127的内容,
for (int i = 0; i < len; i++) {
System.out.println(bytes[i]);
}
}
// 关闭
inputStream.close();
}
}
⭐️ 利用 Scanner 进行字符读取
上述例子中,我们看到了对字符类型直接使用 InputStream 进行读取是非常麻烦且困难的,所以,我们使用一种我们之前比较熟悉的类来完成该工作,就是 Scanner 类。
public class Demo13_Scanner {
public static void main(String[] args) throws IOException {
FileInputStream inputStream = new FileInputStream("./haha.txt");
Scanner scanner = new Scanner(inputStream,"UTF-8");
//hasNext()一个单词一个单词读取,以空格为分割
// while (scanner.hasNext()){
// System.out.println(scanner.next());
// }
//一行一行读取
while (scanner.hasNextLine()){
System.out.println(scanner.nextLine());
}
// try (InputStream is = new FileInputStream("hello.txt")) {
// try (Scanner scanner = new Scanner(is, "UTF-8")) {
// while (scanner.hasNext()) {
// String s = scanner.next();
// System.out.print(s);
// }
// }
// } catch (FileNotFoundException e) {
// throw new RuntimeException(e);
// } catch (IOException e) {
// throw new RuntimeException(e);
// }
}
}
⭐️ OutputStream 概述
方法
说明
OutputStream 同样只是一个抽象类,要使用还需要具体的实现类。我们现在还是只关心写入文件中,所以使用 **FileOutputStream **
public class Demo12_outputStream {
public static void main(String[] args) throws IOException {
File file = new File("./haha.txt");
//根据file对象创建输出流
FileOutputStream outputStream = new FileOutputStream(file);
//以前的写入会被覆盖
//写入文件,写入字节的数据
// outputStream.write(100);
byte[] bytes = {97,98,99,100,101};
outputStream.write(bytes);
// 调用 flush(刷新)操作,将数据刷到设备中。//清空缓存区
outputStream.flush();
// 关闭字节流
outputStream.close();
}
}
⭐️ FileReader与FileWrite
public class Demo14_FileReader {
public static void main(String[] args) throws IOException {
File file = new File("./haha.txt");
FileReader fileReader = new FileReader(file);
while (true){
//读取单一字符,返回-1表示读完了
int read = fileReader.read();
if(read == -1)
break;
//转为字符
System.out.println(Character.toChars(read));
}
}
}
public class Demo15_FileWrite {
public static void main(String[] args) throws IOException {
File file = new File("./haha.txt");
FileWriter fileWriter = new FileWriter(file);
// 需要手动换行
fileWriter.write("你好,Java\n");
fileWriter.write("你好,Java\n");
fileWriter.flush();
fileWriter.close();
}
}
⭐️ PrintWriter
public class Demo16_PrintWriter {
public static void main(String[] args) throws FileNotFoundException {
FileOutputStream outputStream = new FileOutputStream("./haha.txt");
PrintWriter printWriter = new PrintWriter(outputStream);
printWriter.println("hh");
printWriter.println("long");
printWriter.flush();
printWriter.close();
}
}
🌷 练习
⭐️ 练习1
扫描指定目录,并找到名称中包含指定字符的所有普通文件(不包含目录),并且后续询问用户是否要删除该文件
public class Exe01 {
public static void main(String[] args) throws IOException {
System.out.println("请输入要扫描的路径:");
Scanner scanner = new Scanner(System.in);
String rootPath = scanner.next();
//判断路径是否有效
// 是否存在
File root = new File(rootPath);
if(!root.exists()){
System.out.println("路径不存在!");
return;
}
// 是否为目录
if(!root.isDirectory()){
System.out.println("不是目录!");
return;
}
System.out.println("请输入关键字:");
String key = scanner.next();
if(key.equals("")){
System.out.println("关键字不能为空");
}
scan(root,key);
}
private static void scan(File root, String key) throws IOException {
Scanner scanner = new Scanner(System.in);
// 1.先获取root下的所有目录及文件
File[] files = root.listFiles();
// 递归中止条件
if(files == null || files.length == 0){
return;
}
//遍历数组中的每一个文件或目录
for (int i = 0; i < files.length; i++) {
File file = files[i];
//判断是文件还是目录
if(file.isFile()){
//判断文件名是否包含关键字
String fileName = file.getName();
//找到关键字
if (fileName.contains(key)) {
System.out.println("找到文件:" + file.getCanonicalPath() + " ,是否删除(y/n)");
// 接受输入
String order = scanner.next();
//忽略大小写
if(order.equalsIgnoreCase("y")){
file.delete();
System.out.println("删除成功:" + file.getCanonicalPath());
}
}
}else {
scan(file,key);
}
}
}
}
⭐️ 练习2
进行普通文件的复制
public class Exe02 {
public static void main(String[] args) {
// 接受用户的源文件路径
System.out.println("请输入源文件路径:");
Scanner scanner = new Scanner(System.in);
String sourcePath = scanner.next();
// 判断源文件路径是否有效
File sourceFile = new File(sourcePath);
if (!sourceFile.exists()) {
System.out.println("源文件不存在!");
return;
}
//判断是否为文件
if (!sourceFile.isFile()) {
System.out.println("不是一个有效的文件!");
return;
}
// 接受用户输入的目标文件
System.out.println("请输入目标文件路径:");
String destPath = scanner.next();
File destFile = new File(destPath);
if (!destFile.exists()) {
System.out.println("目标文件不存在!");
return;
}
if (!destFile.getParentFile().exists()) {
System.out.println("目标文件的父目录不存在!");
return;
}
// 循环读取写入
// 对于实现了Closeable的类,可以在try()中完成声明,当代码退出try代码块时,自动调用colse方法
try (FileInputStream inputStream = new FileInputStream(sourceFile)) {
FileOutputStream outputStream = new FileOutputStream(destFile);
// 定义一个byte数组,用来保存每次读到的数
byte[] bytes = new byte[1024];
// 循环读取
while (true){
int len = inputStream.read(bytes);
if(len == -1){
break;
}
// 写入
outputStream.write(bytes);
// 刷新
outputStream.flush();
}
} catch (FileNotFoundException e) {
throw new RuntimeException(e);
} catch (IOException e) {
throw new RuntimeException(e);
}
}
}