【java12】java12新特性之File的mismatch方法

发布于:2024-06-28 ⋅ 阅读:(14) ⋅ 点赞:(0)

Java12引入了一个新的方法 mismatch,它属于java.nio.file.Files类。此方法用于比较两个文件的内容,并返回第一个不匹配字节的位置。如果两个文件完全相同,则返回-1

Files.mismatch 方法声明

public static long mismatch(Path path1, Path path2) throws IOException

参数说明:

  • path1: 第一个文件的路径。
  • path2: 第二个文件的路径。

返回值说明:

  • 返回两个文件之间第一个不匹配字节的位置。如果两个文件完全相同,则返回 -1
  • 如果一个文件是另一个文件的前缀,则返回较短文件的长度。

异常说明:

  • IOException: 如果发生I/O错误,抛出IOException异常,例如文件不存在。

Files.mismatch的使用

以下是一个使用Files.mismatch方法的示例代码:

package com.morris.java12;

import java.io.FileWriter;
import java.io.IOException;
import java.net.URISyntaxException;
import java.nio.file.Files;
import java.nio.file.Path;

/**
 * 使用FileMismatch对文件进行比较
 */
public class FileMismatchDemo {
    public static void main(String[] args) throws IOException {

        FileWriter a1 = new FileWriter("d:/a1.txt");
        a1.write("abc中国");
        a1.write("efg");
        a1.write("123");
        a1.close();

        FileWriter a2 = new FileWriter("d:/a2.txt");
        a2.write("abc中国"); // 中文占3个字节
        a2.write("efg");
        a2.write("124");
        a2.close();

        long ap = Files.mismatch(Path.of("d:/a1.txt"), Path.of("d:/a2.txt"));
        System.out.println("a1 and a2 mismatch: " + ap); // 14

        FileWriter b1 = new FileWriter("d:/b1.txt");
        b1.write("abc");
        b1.close();

        FileWriter b2 = new FileWriter("d:/b2.txt");
        b2.write("abc");
        b2.close();

        long bp = Files.mismatch(Path.of("d:/b1.txt"), Path.of("d:/b2.txt"));
        System.out.println("b1 and b2 mismatch: " + bp); // -1
    }
}

运行结果如下:

a1 and a2 mismatch: 14
b1 and b2 mismatch: -1

如果文件内容相同,mismatch方法将返回-1

如果文件内容不同,mismatch方法将返回第一个不匹配字节的位置。

如果文件长度不同,如果一个文件是另一个文件的前缀,mismatch方法将返回较短文件的长度。

这个新方法对文件比较非常有用,可以大大简化需要逐字节比较文件内容的代码。

Files.mismatch的源码分析

public static long mismatch(Path path, Path path2) throws IOException {
    if (isSameFile(path, path2)) {
        return -1;
    }
    byte[] buffer1 = new byte[BUFFER_SIZE];
    byte[] buffer2 = new byte[BUFFER_SIZE];
    try (InputStream in1 = Files.newInputStream(path);
         InputStream in2 = Files.newInputStream(path2)) {
        long totalRead = 0;
        while (true) {
            int nRead1 = in1.readNBytes(buffer1, 0, BUFFER_SIZE);
            int nRead2 = in2.readNBytes(buffer2, 0, BUFFER_SIZE);

            int i = Arrays.mismatch(buffer1, 0, nRead1, buffer2, 0, nRead2);
            if (i > -1) {
                return totalRead + i;
            }
            if (nRead1 < BUFFER_SIZE) {
                // we've reached the end of the files, but found no mismatch
                return -1;
            }
            totalRead += nRead1;
        }
    }
}

底层使用了Arrays.mismatch()比较两个文件的字节数组。


网站公告

今日签到

点亮在社区的每一天
去签到