一、IO操作:两个代码模型
1.1 5个类 1个接口
- File:文件本身的操作
- OutputStream、InputStream :文件内容操作
- Writer、reader :文件内容操作,适合中文
- Serializable
二、File类 文件的操作
2.1 文件的创建和删除
public class FileDemo { public static void main(String[] args) throws IOException { File file = new File("F:\\hello\\hello.txt"); // 1.创建父目录 if(!file.getParentFile().exists()) { file.getParentFile().mkdirs(); } // 2.创建File 和 2.删除文件 if(file.exists()) { // 3.取得文件信息 System.out.println("文件大小:"+file.length()); System.out.println("最后一次修改时间:"+new Date(file.lastModified())); file.delete(); }else { file.createNewFile(); } } }
2.2 递归列出所有的目录以及文件
问题:主线程会暂时阻塞,一只读取文件完成后才会向下执行
解决办法:主线程开启子线程去读取目录
public class ListFiles { public static void main(String[] args) { // 开启子线程 new Thread(() -> { File file = new File("d:"+ File.separator); // 但是主线程会暂时阻塞,一只读取文件完成后才会向下执行 listDir(file); }) .start(); System.out.println("两两不耽搁!"); } /** * 列出所有目录的实现方法 * @param file */ public static void listDir(File file) { // 如果是目录 if(file.isDirectory()) { File result[] = file.listFiles(); if(result != null) { for(int x = 0;x <result.length; x++) { listDir(result[x]); } } } System.out.println(file); } }
三、InputStream、OutputStream 字节流操作
- File类不支持文件内容的处理,必须使用输入流和输出流。
- 流分为:
- 字节流:InputStream 字节输入流【原生】
OutputStream 字符输出流
- 字符流:Writer 适合处理中文【处理后】
reader
- 用完必须关闭!!!
- 字节流与字符流之间的差异:
1.代码操作形式区别不大
2.字节流优先考虑
3.处理中文,使用字符流【需要使用内存缓冲来处理】
3.1 OutPutStreamDemo将文件的内容输出
public class OutPutStreamDemo { public static void main(String[] args) throws Exception { // 1.文件内容的输出 File file = new File("d:"+ File.separator+"hello.txt"); // 2.保证附目录存在 if(!file.getParentFile().exists()) { file.getParentFile().mkdirs(); } // 3.实例化,只能进行文件处理,后面追加TRUE 为追加内容 OutputStream output = new FileOutputStream(file,true); // \r\n 换行 String msg= "wwwwww\r\n"; output.write(msg.getBytes()); // 4.关闭 output.close(); } }
3.2 InputStreamDemo 读取文件的内容
public class InputStreamDemo { public static void main(String[] args) throws Exception { // 读取文件 File file = new File("d:"+ File.separator+"hello.txt"); if(file.exists()) { InputStream input = new FileInputStream(file); // 每次读取最大的数量 byte data[] = new byte[1024]; // 数据读取到数组之中 int len = input.read(data); System.out.println("内容是:"+ new String(data,0,len)); // 关闭 input.close(); } } }
四、Writer、Reader 字符适合处理中文数据,Writer时字符输出流的处理 抽象类
4.1 WriterDemo 读取文件
public class WriterDemo { public static void main(String[] args) throws Exception { // 1.读取文件 File file = new File("d:"+ File.separator+"hello.txt"); // 2.保证附目录存在 if(!file.getParentFile().exists()) { file.getParentFile().mkdirs(); } String msg = "中国的迪丽热巴"; // 3.写入中文到文件中 Writer out = new FileWriter(file); out.write(msg); out.close(); } }
4.2 ReaderDemo 读取文件的内容
public class ReaderDemo { public static void main(String[] args) throws Exception { // 1.读取文件 File file = new File("d:"+ File.separator+"hello.txt"); // 2.判断文件是否存在 if(file.exists()) { Reader in = new FileReader(file); char data[] = new char[1024]; int len = in.read(data); System.out.println(new String(data,0,len)); in.close(); } } }
五、综合案例:实现文件的拷贝
/** * @author captain * @date 2020年2月3日 * 实现文件的拷贝 * 思路:流模式,选择字节流还是字符流?应该选择字节流! * 1.开辟数组:文件的长度,将所有的数据一次性读入数组中,输出保存。【数据太大不合适 TB PB ZB,内存装不下】 * 2.边读边写:较为合适 */ public class CopyFileDemo { public static void main(String[] args) { // 1.java copy 源文件路径 目标文件路径 if(args.length !=2 ) { System.out.println("输入命令有误!"); System.exit(1); } // 2.判断原文件的路径是否存在 if(CopyUtil.fileExists(args[0])) { CopyUtil.createParentDirectory(args[1]); System.out.println(CopyUtil.copy(args[0], args[1]) ? "文件拷贝成功!":"文件拷贝失败!"); }else { System.out.println("对不起,源文件不存在!"); } } } /** * 文件拷贝的功能 * 1.需要判断拷贝的源文件是否存在 * 2.目标文件的父路径是否存在,不存在创建 * 3.执行拷贝 */ class CopyUtil{ private CopyUtil() { } // 判断要拷贝的原路径是否存在 public static boolean fileExists(String path) { return new File(path).exists(); } // 判断是否存在父路径,不存在则创建 public static void createParentDirectory(String path) { File file = new File(path); if(!file.getParentFile().exists()) { file.getParentFile().mkdirs(); } } // 拷贝 public static boolean copy(String srcPath, String desPath) { // 文件的拷贝的标记 boolean flag = false; File inFile = new File(srcPath); File outFile = new File(desPath); InputStream input = null; OutputStream output = null; try { output = new FileOutputStream(outFile); input = new FileInputStream(inFile); // 文件拷贝 copyHandle(input,output); flag = true; }catch(Exception e){ flag = false; }finally { try { input.close(); output.close(); }catch(Exception e) {} } return flag; } // 具体文件的拷贝处理 public static void copyHandle(InputStream input, OutputStream output) throws Exception{ // InputStream有一个读取单个字节的方法 ,OutputStream有一个。。。 int temp = 0; byte data[] = new byte[2048]; // 读完为止 while((temp = input.read(data)) != -1) { output.write(data,0,temp); } } }