Guava包学习---I/O

时间:2022-03-16 06:43:40

Guava的I/O平时使用不太多,目前项目原因导致基本上只有在自己写一些文本处理小工具才用得到。但是I/O始终是程序猿最常遇到的需求和面试必问的知识点之一。同时Guava的I/O主要面向是时JDK5和JDK6的时候的设计,现在已经到了JDK8,然而由于懒惰并没有仔细研究这之间的差别,反正就慢慢看吧。

Guava提供了一个Files的类,用final修饰了,所以直接用就行了,也不要再想着扩展了,里面的方法很多:

Guava包学习---I/O

获得一个BufferedReader/bufferedwriter,简单就是从file->fileinputstream->inputstreamreader-bufferedreader,一路生成过去:

 public static BufferedReader newReader(File file, Charset charset)
throws FileNotFoundException {
checkNotNull(file);
checkNotNull(charset);
return new BufferedReader(
new InputStreamReader(new FileInputStream(file), charset));
}
  public static BufferedWriter newWriter(File file, Charset charset)
throws FileNotFoundException {
checkNotNull(file);
checkNotNull(charset);
return new BufferedWriter(
new OutputStreamWriter(new FileOutputStream(file), charset));
}

获得一个Guava自定义的ByteSource对象:

public static ByteSource asByteSource(File file) {
return new FileByteSource(file);
}

这个FileByteSource其实就是提供了获得文件流、文件大小、获得字节数组、toString()等方法。

获得一个Guava自定义的ByteSink对象:

 public static ByteSink asByteSink(File file, FileWriteMode... modes) {
return new FileByteSink(file, modes);
}

ByteSink的概念稍微有点绕,看下源码:

private static final class FileByteSink extends ByteSink {

    private final File file;
private final ImmutableSet<FileWriteMode> modes; private FileByteSink(File file, FileWriteMode... modes) {
this.file = checkNotNull(file);
this.modes = ImmutableSet.copyOf(modes);
} @Override
public FileOutputStream openStream() throws IOException {
return new FileOutputStream(file, modes.contains(APPEND));
} @Override
public String toString() {
return "Files.asByteSink(" + file + ", " + modes + ")";
}
}

就是给你一个对象,然后这个对象可以将内容追加到file里面去,它可以提供对该文件的追加操作的输出流。

接下来又是一对输入输出的Char对象:

 public static CharSource asCharSource(File file, Charset charset) {
return asByteSource(file).asCharSource(charset);
}
public static CharSink asCharSink(File file, Charset charset,
FileWriteMode... modes) {
return asByteSink(file, modes).asCharSink(charset);
}

输入对象提供了比如readlines()、concat组合两个sources并返回组合后的内容。

输出对象提供了比如获得writer、writelines等内容。

接下来的几个方法可能是更常用和方便的方法了。

获得字节数组:

  public static byte[] toByteArray(File file) throws IOException {
return asByteSource(file).read();
}

获得文件内容的String对象:

  public static String toString(File file, Charset charset) throws IOException {
return asCharSource(file, charset).read();
}

为文件写入一个字节数组的内容:

  public static void write(byte[] from, File to) throws IOException {
asByteSink(to).write(from);
}

把一个文件内容拷贝到一个输出流中:

  public static void copy(File from, OutputStream to) throws IOException {
asByteSource(from).copyTo(to);
}

把一个文件拷贝到另外一个地方:

  public static void copy(File from, File to) throws IOException {
checkArgument(!from.equals(to),
"Source %s and destination %s must be different", from, to);----------两个文件必须不同
asByteSource(from).copyTo(asByteSink(to));
}

把一个字符序列写入文件:

 public static void write(CharSequence from, File to, Charset charset)
throws IOException {
asCharSink(to, charset).write(from);
}

把一个文件拷贝追加后另外一个文件后面:

 public static void copy(File from, Charset charset, Appendable to)
throws IOException {
asCharSource(from, charset).copyTo(to);
}

判断两个文件是否一致:

 public static boolean equal(File file1, File file2) throws IOException {
checkNotNull(file1);
checkNotNull(file2);
if (file1 == file2 || file1.equals(file2)) {
return true;
} /*
* Some operating systems may return zero as the length for files
* denoting system-dependent entities such as devices or pipes, in
* which case we must fall back on comparing the bytes directly.
*/
long len1 = file1.length();
long len2 = file2.length();
if (len1 != 0 && len2 != 0 && len1 != len2) {-------------考虑到操作系统级别的不同,仅仅length并不完整
return false;
}
return asByteSource(file1).contentEquals(asByteSource(file2));
}

创建一个临时目录((-__-)b,这个方法有什么用吗?):

 public static File createTempDir() {
File baseDir = new File(System.getProperty("java.io.tmpdir"));
String baseName = System.currentTimeMillis() + "-"; for (int counter = 0; counter < TEMP_DIR_ATTEMPTS; counter++) {
File tempDir = new File(baseDir, baseName + counter);
if (tempDir.mkdir()) {
return tempDir;
}
}
throw new IllegalStateException("Failed to create directory within "
+ TEMP_DIR_ATTEMPTS + " attempts (tried "
+ baseName + "0 to " + baseName + (TEMP_DIR_ATTEMPTS - 1) + ')');
}

创建一个文件(如果不存在)或者修改一下该文件的末次修改时间(如果已经存在),就相当于linux的touch命令:

  public static void touch(File file) throws IOException {
checkNotNull(file);
if (!file.createNewFile()
&& !file.setLastModified(System.currentTimeMillis())) {
throw new IOException("Unable to update modification time of " + file);
}

为要创建的文件创建路径中出现的其他父文件夹路径然后创建这个File,需要其中某一步执行失败,可以会已经创建了一些父文件夹出来而无法收回:

 public static void createParentDirs(File file) throws IOException {
checkNotNull(file);
File parent = file.getCanonicalFile().getParentFile();
if (parent == null) {--------本身就是根目录
return;
}
parent.mkdirs();
if (!parent.isDirectory()) {
throw new IOException("Unable to create parent directories of " + file);
}
}

移动文件:

  public static void move(File from, File to) throws IOException {
checkNotNull(from);
checkNotNull(to);
checkArgument(!from.equals(to),
"Source %s and destination %s must be different", from, to); if (!from.renameTo(to)) {
copy(from, to);
if (!from.delete()) {
if (!to.delete()) {
throw new IOException("Unable to delete " + to);
}
throw new IOException("Unable to delete " + from);
}
}
}

只读第一行:

  public static String readFirstLine(File file, Charset charset)
throws IOException {
return asCharSource(file, charset).readFirstLine();
}

用的最多的一个方法,把文件转成一个List<String>:

public static List<String> readLines(File file, Charset charset)
throws IOException {
// don't use asCharSource(file, charset).readLines() because that returns
// an immutable list, which would change the behavior of this method
return readLines(file, charset, new LineProcessor<List<String>>() {
final List<String> result = Lists.newArrayList(); @Override
public boolean processLine(String line) {
result.add(line);
return true;
} @Override
public List<String> getResult() {
return result;
}
});
}

返回你定义格式的内容,需要提供一个回掉函数,回掉函数可以返回一个fboolean,如果返回false就结束读取,也就是你可以在这里去自定义自己想要的结束位置:

  public static <T> T readLines(File file, Charset charset,
LineProcessor<T> callback) throws IOException {
return asCharSource(file, charset).readLines(callback);
}
  public static <T> T readBytes(File file, ByteProcessor<T> processor)
throws IOException {
return asByteSource(file).read(processor);
}

返回一个文件的Hash值,你可以自定义hash算法:

  public static HashCode hash(File file, HashFunction hashFunction)
throws IOException {
return asByteSource(file).hash(hashFunction);
}

将文件内容全量映射到内存中,就是JDK1.4以后NIO里面独立于JVM堆之外的直接内存,用于加速IO处理的:

  public static MappedByteBuffer map(File file, MapMode mode)
throws IOException {
checkNotNull(file);
checkNotNull(mode);
if (!file.exists()) {
throw new FileNotFoundException(file.toString());
}
return map(file, mode, file.length());
}
  public static MappedByteBuffer map(File file, MapMode mode, long size)
throws FileNotFoundException, IOException {
checkNotNull(file);
checkNotNull(mode); Closer closer = Closer.create();
try {
RandomAccessFile raf = closer.register(
new RandomAccessFile(file, mode == MapMode.READ_ONLY ? "r" : "rw"));
return map(raf, mode, size);
} catch (Throwable e) {
throw closer.rethrow(e);
} finally {
closer.close();
}
}

返回准确的文件路径:

 public static String simplifyPath(String pathname) {
checkNotNull(pathname);
if (pathname.length() == 0) {
return ".";
} // split the path apart
Iterable<String> components =
Splitter.on('/').omitEmptyStrings().split(pathname);
List<String> path = new ArrayList<String>(); // resolve ., .., and //
for (String component : components) {
if (component.equals(".")) {
continue;
} else if (component.equals("..")) {
if (path.size() > 0 && !path.get(path.size() - 1).equals("..")) {
path.remove(path.size() - 1);
} else {
path.add("..");
}
} else {
path.add(component);
}
} // put it back together
String result = Joiner.on('/').join(path);
if (pathname.charAt(0) == '/') {
result = "/" + result;
} while (result.startsWith("/../")) {
result = result.substring(3);
}
if (result.equals("/..")) {
result = "/";
} else if ("".equals(result)) {
result = ".";
} return result;
}

Guava包学习---I/O的更多相关文章

  1. Guava包学习---Lists

    Guava包是我最近项目中同事推荐使用的,是google推出的库.里面的功能非常多,包括了集合.缓存.原生类型支持.并发库.通用注解.字符串处理.IO等.我们项目中使用到了guava依赖,但是实际上只 ...

  2. Guava包学习--EventBus

    之前没用过这个EventBus,然后看了一下EventBus的源码也没看明白,(-__-)b.反正大概就是弄一个优雅的方式实现了观察者模式吧.慢慢深入学习一下. 观察者模式其实就是生产者消费者的一个变 ...

  3. Guava包学习-Cache

    这段时间用到了ehcache和memcache,memcache只用来配置在tomcat中做负载均衡过程中的session共享,然后ehcache用来存放需要的程序中缓存. Guava中的Cache和 ...

  4. Guava包学习---Maps

    Maps包方法列表: 还是泛型创建Map: public static <K, V> HashMap<K, V> newHashMap() { return new HashM ...

  5. Guava包学习--Hash

    我们HashMap会有一个rehash的过程,为什么呢?因为java内建的散列码被限制为32位,而且没有分离散列算法和所作用的数据,所以替代算法比较难做.我们使用HashMap的时候它自身有一个reh ...

  6. Guava包学习---Bimap

    Bimap也是Guava中提供的新集合类,别名叫做双向map,就是key->value,value->key,也就是你可以通过key定位value,也可以用value定位key. 这个场景 ...

  7. Guava包学习-Multimap

    它和上一章的MultiSet的继承结果很相似,只不过在上层的接口是Multimap不是Multiset. Multimap的特点其实就是可以包含有几个重复Key的value,你可以put进入多个不同v ...

  8. Guava包学习---Sets

    Sets包的内容和上一篇中的Lists没有什么大的区别,里面有些细节可以看一下: 开始的创建newHashSet()的各个重载方法.newConcurrentHashSet()的重载方法.newTre ...

  9. Guava包学习--Table

    Table,顾名思义,就好像HTML中的Table元素一样,其实就是行+列去确定的值,更准确的比喻其实就是一个二维矩阵. 其实它就是通过行+列两个key去找到一个value,然后它又containsv ...

随机推荐

  1. 创建ASP&period;NET Core MVC应用程序&lpar;3&rpar;-基于Entity Framework Core&lpar;Code First&rpar;创建MySQL数据库表

    创建ASP.NET Core MVC应用程序(3)-基于Entity Framework Core(Code First)创建MySQL数据库表 创建数据模型类(POCO类) 在Models文件夹下添 ...

  2. opengl

    基于OpenGL ES的GLfixed类型使用 OpenGL ES中引入了GLfixed类型.这个类型一般被定义为int,32位.高16位表示整数部分,低16位表示小数部分.由于其整数部分和小数部分所 ...

  3. phpcms 修改后台 主页面的模板

    代码在phpcms/modules/admin/templates/main.tpl.php 在该文件修改就可以修改 phpcms后台管理系统的 首页面.

  4. NSString&amp&semi;NSMutableString常用操作梳理(转)

    作者:弦苦 授权本站转载. 上一篇梳理了NSArray&NSMutableArray常用操作,这次来梳理一下Objective-C中每天都要用到的字符串处理类——NSString. Objec ...

  5. 海马玩模拟器——搭建React Native环境

    Visual Studio Emulator for Android 模拟器国内这网络环境不太用,所以使用海马玩模拟器,给大家推荐一下! 下面开始配置环境: 1)下载1.8+JDK,配置JDK环境参考 ...

  6. django 如何动态使用Q查询函数

    这个Q和F用得少, 需要时,总是独立的存在于那时,显得有些突兀, 这次想将filter,order,Q集合在一起, 查询了很多资料,还是有一些困难, 但即可以将Q查询比较优雅的动态生成. 比如: # ...

  7. WCF 与 Windows Store Client App

    首先复习下WCF: WCF实际上是构建了一个框架,这个框架实现了在互联系统中各个Application之间如何通信.使得Developers和Architect在构建分布式系统中,无需在考虑如何去实现 ...

  8. strstr&lpar;&rpar;,strchr&lpar;&rpar;

    strstr($a, $b)和strchr()一样,起的别名,表示查找$a中第一次出现$b,并返回字符串的剩余部分: .strrchr()从后往前查第一个出现的 直接写两行代码: <?php $ ...

  9. 关于截取字符串substr和substring两者的区别

    https://blog.csdn.net/adley_function/article/details/52130762 substr和substring两个都是截取字符串的. 两者有相同点,如果只 ...

  10. Spring学习&lpar;十三&rpar;-----Spring 表达式语言&lpar;Spring EL&rpar;

    本篇讲述了Spring Expression Language —— 即Spring3中功能丰富强大的表达式语言,简称SpEL.SpEL是类似于OGNL和JSF EL的表达式语言,能够在运行时构建复杂 ...