【0】README

0.1) 本文描述转自 core java volume 2, 旨在理解 java流与文件——操作文件 的相关知识;
0.2) for source code, please visit https://github.com/pacosonTang/core-java-volume/blob/master/coreJavaAdvanced/chapter1/FileAndPathTest.java)


【1】Path

1.1)Path: 表示的是一个目录名序列, 其后还可以跟一个文件名;路径中的第一个部件可以是跟部件, 例如 / 或 C:/ , 而有序访问的根部件,取决于文件系统;(干货——Path类定义)

  • 1.1.1)以根目录开始的是绝对路径,否则就是相对路径;如,
    Path absolute = Paths.get(“/home”, “cay”);
    Path relative = Paths.get(“myprog”, “cay”);
  • 1.1.2) 静态的 Paths.get 方法: 接受一个或多个字符串, 并将它们用默认文件系统的路径分隔符连接起来;
  • 1.1.3)get方法: 可以获取包含多个部件构成的单个字符串, 如, 可以像下面这样从配置文件中读取路径:
    String baseDir = props.getProperty(“base.dir”);
    Path basePath = Paths.get(baseDir);

Attention)

  • A1)路径不必对应着某个实际存在的文件, 他仅仅只是一个抽象的名字序列;
  • A2)当你想要创建文件时, 首先要创建一个路径,然后才调用方法去创建对应的文件;

1.2)组合或解析路径是司空见惯的操作,调用 p.resolve(q) 将按照下列规则返回一个路径: (干货——p后面跟着q)

  • 1.2.1)如果 q 是绝对路径, 则结果就是q;
  • 1.2.2)否则,根据文件系统的规则, 将p 后面跟着q 作为结果;
  • 1.2.3) resolve 方法有一种快捷方式,它接收一个字符串而不是路径:
    Path workPath = basePath.resolve(“work”);

  • 1.2.4)还有一个 方法: resolveSibling
    它通过解析指定路径的父路径产生其兄弟路径, 例如, 如果workPath 是 /opt/myapp/work, 那么下面的调用
    Path tempPath = workPath.resolveSibling(“temp”) 将创建 /opt/myapp/temp; (干货——创建兄弟路径)

  • 1.2.5)resolve的对立面是 relative: 即调用 p.relativeze(r) 将产生路径q, 对q进行解锁产生r;
  • 1.2.6)normalize 方法:移除所有冗余的 . 和 .. 部件(或者文件系统认为冗余的所有部件);
    如规范化 /home/cay/../fred/./ myprog 将产生 /home/fred/myprog

  • 1.2.7)toAbsolutePath 方法: 将产生给定路径的绝对路径, 该绝对路径从根部件开始;
  • 1.2.8) Path类有许多方法用来将路径断开以及和其它路径进行组合。如:
    Path p = Paths.get(“/home”, “myprog.properties”);
    Path parent = p.getParent();
    Path file = p.getFilename();
    Path root = p.getRoot();

  • Attention) 你可能需要与遗留系统的API 交互, 它们使用的是 File 类而不是 Path 类。 Path类有一个toFile 方法, 而 File 类也有一个 toPath 方法;

【2】读写文件

2.1)Files 类可以使得普通文件操作变得快捷;

  • 2.1.1)用下面的方式很容易的读取文件的所有内容:
    byte[] bytes = Files.readAllBytes(path);
  • 2.1.2)如果想将文件当做字符串输入, 则:
    String content = enw String(bytes, charset);
  • 2.1.3)如果希望 将文件当做行序列输入, 则:
    List lines = Files.readAllLines(path, charset);
  • 2.1.4)相反地, 如果希望写出一个字符串到文件中, 则:
    Files.write(path, content.getBytes(charset));

  • 2.1.5)向指定文件追加内容,则:
    Files.write(path, content.getBytes(charset), StandardOpoenOption.APPEND);
  • 2.1.6)还可以用下面的语句将一行集合写出到文件中:
    Files.write(path, lines);

  • 2.1.7) 如果要处理的文件长度过大, 或者是二进制文件, 那么还是应该使用所熟悉的流或者读入器/ 写出器;
    InputStream is = Files.newInputStream(path);
    OutputStream os = Files.newOutputStream(path);
    Reader reader = Files.newBufferedReader(path, charset);
    Writer writer = Files.newBufferedWriter(path, charset);

  • 2.1.8)总结: 这些便捷方法可以将你从处理 FileInputStream, FileInputStream, BufferedReader 和 BufferedWriter 的繁复操作中解脱出来;


【3】复制、移动和删除文件

3.1)复制文件: Files.copy(fromPath, toPath);
3.2)移动文件 (复制并删除源文件): Files.move(frompath, topath);

  • 3.2.1)如果目标路径已经存在,那么复制或移动将失败;
  • 3.2.2)如果想要覆盖已有的目标路径, 可以使用 REPLACE_EXISTING 选项;
  • 3.2.3)如果想要复制文件的属性, 可以使用 COPY_ATTRIBUTES ;
  • 3.2.4)也可以同时使用者两个选项:
    Files.copy(fromPath, toPath, StandardCopyOption.REPLACE_EXISTING, StandardCopyOption.COPY_ATTRIBUTES);
  • 3.2.5)可以将移动操作定义为 原子性的(要么全部成功, 要么就不成功)
    Files.move(fromPath, toPath, StandardCopyOption.ATOMIC_MOVE);
  • 3.2.6)最后删除文件,调用:
    Files.delete(path);
  • 3.2.7)如果要删除的文件不存在, delete 方法就会抛出异常;使用 deleteIfExists 不会抛出异常,
    boolean deleted = Files.deleteIfExists(path); 该方法 deleteIfExists 还可以用来移除空目录;


【4】 创建文件和目录

4.1)创建目录: Files.createDirectory(path);
4.2)创建中间目录: Files.createDirectories(path); (迭代创建目录)

  • 4.2.1)创建空文件: Files.createFile(path)
  • 4.2.2)有些便捷方法用来在给定位置或系统指定位置创建临时文件或 临时目录:
    Path newPath = FIles.createTempFile(dir, prefix, suffix);
    Path newPath = FIles.createTempFile( prefix, suffix);
    Path newPath = FIles.createTempFile(dir, prefix);
    Path newPath = FIles.createTempFile(prefix);
  • 其中,dir 是一个Paht对象,prefix 和 suffix 是可以为 null 的字符串;例如,调用 Files.createTempFile(null, “.txt”) 可能返回一个像 /tmp/2345646464646464.txt这样的路径;


【5】 获取文件信息

5.1)下面的静态方法都将返回一个boolean值, 表示检查路径的某个属性的结果:
exists + isHidden + isReadable + isWritable + isExecutable + isRegularFile + isDirectory + isSymbolicLink
5.2)size 方法将返回文件的字节数:
long size = Files.size(path);
5.3)getOwner: 将文件的所有者作为 java.nio.file.attribute.UserPrincipal 的一个实例返回;
5.4)所有的文件系统都会报告一个基本属性集, 它们被封装在 BasicFileAttributes 接口中, 这些属性与上述信息有部分重叠。基本文件属性包括:

  • 5.4.1)创建文件, 最后一次访问以及最后一次修改时间;
  • 5.4.2)文件时常规文件, 目录还是符号链接, 或者都不是;
  • 5.4.3)文件大小;
  • 5.4.4)文件主键, 这是某种类的对象, 具体所属类与文件系统相关, 有可能是文件的唯一标识符,也有可能不是;
  • 5.4.5)要获取这些属性,调用
    BasicFileAttributes attributes = files.readAttributes(path, BasicFileAttributes.class);

5.5) 如果你了解到用户的文件系统兼容 POSIX, 可以获取一个 PosiXFileAttributes 实例:
PosiXFileAttributes attributes = files.readAttributes(path, PosiXFileAttributes.class);
然后从中找到组拥有者, 拥有者,组,以及访问权限;


【6】 迭代目录中的文件

6.1)problem+solution

  • 6.1.1)problem: 旧File 类有一个方法,用来获取由一个目录的所有文件构成的数组, 当目录包含大量的文件时,方法性能非常低;
  • 6.1.2)solution: File类设计了一个方法, 产生一个 Iterable 对象, 如:
    try(DirectoryStream entries = Files.newDirectoryStream(dir))
    {
    for(Path entry : entries)
    process entries
    }
  • 6.1.3)try 语句块用来确保目录流可以被正确关闭。访问目录中的项并没有具体的顺序, 可以用 glob 模式来过滤:(干货——带资源的try语句块)
    try(DirectoryStream entries = Files.newDirectoryStream(dir, “*.java”));

  • Warning)如果使用 Windows 的 glob 语法, 则必须对反斜杠转移两次:一次为 glob 语法转义, 一次为java 字符串转义:Files.newDirectoryStream(dir, “C:\\”)

6.2)如果想要访问某个目录的子孙成员, 转而调用 walkFileTree 方法, 并向其传递一个 FileVisitor 类型的对象, 这个对象会得到下面通知:

  • 6.2.1)在遇到一个文件或目录时: FileVisitResult visitFile(T path, BasicFileAttributes attrs)
  • 6.2.2) 在一个目录被处理前: FileVisitResult preVisitFile(T dir, IOException ex)
  • 6.2.3) 在一个目录被处理后: FileVisitResult postVisitFile(T dir, IOException ex)
  • 6.2.4) 在试图访问文件或目录时发生错误, 例如没有权限打开目录: FileVisitResult visitFileFailed(path, IOException)

6.3) 对上述每种情况, 都可以指定是否希望执行下面的操作:

  • 6.3.1)继续访问下一个文件: FileVisitResult.CONTINUE;
  • 6.3.2)继续访问,但不在访问这个目录下的任何项了: FileVisitResult.SKIP_SUBTREE;
  • 6.3.3)继续访问, 但是不在访问这个文件的兄弟文了: FileVisitResult.SKIP_SIBLINES;
  • 6.3.4)终止访问: FileVisitResult.TRIMINATE ;

6.4) 当有任何方法抛出异常时, 就会终止访问, 而这个异常会从 walkFileTree 方法中抛出;

  • Attention) FileVisitor 接口是泛化类型, 但是你也太可能会使用 除开 FileVisit 之外的东西; walkFileTree 方法可以接收 FileVisitor

【7】 ZIP 文件系统

7.1)建立一个文件系统, 包含 ZIP 文档中的所有文件;
FileSystem fs = FileSystems.newFIleSystem(Paths.get(zipname), null);

  • 7.1.1)如果知道文件名,从ZIP 文档中复制出这个文件就变得很容易:
    Files.copy(fs.getPath(sourceName), targetPath);
  • 7.1.2)要列出ZIP 文档中的所有文件, 可以遍历文件树:
FileSystem fs = FileSystems.newFIleSystem(Paths.get(zipname), null)
Files.walkFileTree(fs,.getPath("/"), new SimpleFileVisitor<Path>(){public FileVisitResult visitFile(Path file , BasicFIleAttributes attrs){println(file);return FileVisitResult.CONTINUE;}}
)

java流与文件——操作文件相关推荐

  1. Linux——权限|shell运行原理——外壳程序|Linux权限的概念|对人操作|角色和文件操作|文件类型访问权限|修改权限ugo+-|8进制|修改权限|更改文件的拥有

    目录 shell运行原理--外壳程序 Linux权限的概念 对人操作 角色和文件操作 文件类型

  2. 【Delphi入门】文件系统(文件分类 文件文本变量 文件操作 文件流操作)

    文件分类 文本文件(TextFile) & 二进制文件(Flie) 二进制形式存放数据占有存储空间较少,但不直观:文本文件与之相反 文件是由相同类型的数据元素组成的序列.在DELPHI中对文件 ...

  3. java files_Java NIO Files 操作文件

    Java7中文件IO发生了很大的变化,专门引入了很多新的类: import java.nio.file.DirectoryStream; import java.nio.file.FileSystem ...

  4. VC 文件操作(文件查找,打开/保存,读/写,复制/删除/重命名)

    右击项目->属性->字符集:使用多字节字符集. 这样可以使用char到CString的转化. char sRead[20] = ""; CString strtest ...

  5. 【C 语言】文件操作 ( 文件加密解密 | 使用第三方 DES 加密解密库 | 头文件导入 | 兼容 C++ 语言 | 加密解密函数说明 )

    文章目录 一.导入第三方库头文件 二.头文件说明 1.兼容 C++ 语言 2.头文件导入限制 3.加密解密函数说明 一.导入第三方库头文件 对文件进行加密 , 将文件中的数据分成若干块 , 一块一块的 ...

  6. python文件读取与输出_python基本文件操作(文件输入和输出)

    文件输入输出中常用的文件对象方法: open: 返回一个新的文件对象,调用该对象的上的方法可对文件进行任何操作 readline: 读取一行数据包括结尾的换行符在内 write: 将数据写入文件中 c ...

  7. Python基础day07 作业解析【文件操作(文件读写、文件夹操作)】

    视频.源码.课件.软件.笔记:超全面Python基础入门教程[十天课程]博客笔记汇总表[黑马程序员] Python基础day07[文件读写.文件夹操作.面向对象(类.对象)] 目录 加强训练 题目1 ...

  8. Linux学习笔记6 文件操作——文件描述符

    基于文件描述符的文件操作 进程一启动,内核就打开了三个描述符,0(标准输入 STDIN),1(标准输出STDOUT), 2(标准错误输出STDERR).Linux用整形数做文件操作,因此称为文件描述符 ...

  9. Visual C++网络编程经典案例详解 第8章 网络文件传输 使用api函数操作文件 操作文件 FlushFileBuffers函数

    如果想数据被立即写入文件所在的磁盘中 可以使用函数FlushFileBuffers() 将数据强制写入文件中 原型 BOOL FlushFileBuffers(HANDLE hFile); 函数唯一参 ...

最新文章

  1. aws lambda使用_使用AWS Lambda安排Slack消息
  2. [Java基础]类和接口的关系
  3. CSS3--5.颜色属性
  4. 第60课 比特超市 《小学生C++趣味编程》
  5. 华为的数字化转型与数据治理
  6. SVG基础知识 Adobe Illustrator绘制SVG
  7. underscore.js中的节流函数debounce及trottle
  8. 用python给自己DIY一款小说阅读器
  9. tortoise清理本地分支_如何删除TortoiseHg中的意外分支?
  10. 中兴2016笔试题答案Java_中兴Java笔试题
  11. 将RDL报表转换成RDLC报表的函数
  12. China Unicom笔面试
  13. 动漫人物脸型怎么画?如何画好动漫人物脸型?
  14. 无线网络摄像头服务器,无线摄像头云服务器
  15. Android中的手机屏幕像素的几种获取方式
  16. java war包混淆,spring项目的代码混淆(proguard)
  17. 计算机一级底纹颜色怎么设置,word2016文字字形和颜色设置及文字底纹效果方法...
  18. Numpy:关于flatten的理解
  19. vue路由传参—params—query
  20. SeEnableDelegationPrivilege权限的利用

热门文章

  1. CF1396B Stoned Game(博弈论)
  2. 动态区间第k小:树状数组套权值线段树
  3. YBTOJ:字符串题(KMP)
  4. P4688-[Ynoi2016]掉进兔子洞【莫队,bitset】
  5. Loj#3130-「COCI 2018.12」Praktični【线性基】
  6. 学习手记(2018.11.30~2019.6.6)——养老时间
  7. HDU5126 stars(4维偏序->cdq套cdq+树状数组)
  8. Gym102059A Coloring Roads
  9. Hadoop生态hive(一)介绍
  10. 聚集索引、辅助索引、覆盖索引、联合索引