Java检测重复图片的核心是图像哈希,常用aHash、pHash、dHash三种算法;dHash推荐入门,用BufferedImage缩放为9×8灰度图,比较相邻像素差生成64位二进制指纹,汉明距离≤3–5视为重复。
Java 检测重复图片,核心思路是用图像哈希(Image Hash)把图片转成固定长度的指纹,再比对指纹相似度。不是逐像素比较,而是提取视觉特征后降维,兼顾速度和鲁棒性(对缩放、亮度微调、轻微压缩不敏感)。
常用且适合 Java 实战的有三种:
不需要复杂依赖,JDK 自带 BufferedImage 就够用:
public static String dHash(BufferedImage img) {
int width = 9, height = 8;
Buffer
edImage resized = resizeGray(img, width, height); // 缩放+灰度
StringBuilder sb = new StringBuilder();
for (int i = 0; i < height; i++) {
for (int j = 0; j < width - 1; j++) {
int pixelLeft = resized.getRGB(j, i) & 0xFF;
int pixelRight = resized.getRGB(j + 1, i) & 0xFF;
sb.append(pixelLeft > pixelRight ? "1" : "0");
}
}
return sb.toString(); // 返回 64 字符二进制串
}
比对时直接计算汉明距离(异或后数 1 的个数),≤ 3–5 通常视为重复。
long,比对用 Long.bitCount(h1 ^ h2),性能提升 5–10 倍。基本上就这些。Hash 不是万能——完全翻转、大幅裁剪、加水印的图可能漏判,但对日常去重、相册整理、上传防重,dHash + 汉明阈值已足够好用。