
本文介绍一种基于 sha-256 哈希比对的可靠方案,用于扫描目录中所有文件、精准识别内容重复项,并提供可选的自动清理逻辑,兼顾准确性与操作安全性。
本文介绍一种基于 sha-256 哈希比对的可靠方案,用于扫描目录中所有文件、精准识别内容重复项,并提供可选的自动清理逻辑,兼顾准确性与操作安全性。
在处理大量用户上传或备份文件时,重复内容不仅浪费存储空间,还可能引发管理混乱。PHP 提供了 hash_file() 函数,能高效计算文件内容的 SHA-256 哈希值——该值具备强抗碰撞性,只要文件内容完全一致,哈希必然相同;反之,哪怕一个字节差异,哈希也截然不同。因此,哈希是识别真正“内容重复”(而非仅文件名相同)的黄金标准。
以下是一个结构清晰、生产就绪的实现流程:
1. 扫描并构建哈希-文件映射数组
避免将文件名与哈希扁平化混存(如原代码中的 array_push($arr, $name, $hash)),而应使用关联结构,确保语义明确、便于后续分组:
$localfileslist = [];
$scanPath = $_GET['name'] ?? __DIR__; // 建议增加路径校验与安全过滤
$localfiles = glob($scanPath . '/*');
foreach ($localfiles as $localfile) {
if (is_file($localfile) && is_readable($localfile)) {
$hash = hash_file('sha256', $localfile);
if ($hash !== false) { // 防止因权限/损坏导致哈希失败
$localfileslist[] = ['name' => $localfile, 'hash' => $hash];
}
}
}2. 按哈希值分组文件
使用 array_reduce() 将所有同哈希文件路径归入同一键下,形成 $hash => [path1, path2, ...] 结构:
立即学习“PHP免费学习笔记(深入)”;
$grouped = array_reduce($localfileslist, function ($groups, $item) {
$hash = $item['hash'];
if (!isset($groups[$hash])) {
$groups[$hash] = [];
}
$groups[$hash][] = $item['name'];
return $groups;
}, []);3. 筛选出真正的重复组(≥2 个文件)
$duplicates = array_filter($grouped, fn($paths) => count($paths) > 1);
此时 $duplicates 是一个关联数组,每个键为重复哈希值,对应值为该哈希下所有文件路径数组。例如:
[ 'a1b2c3...' => ['/path/a.txt', '/path/b.txt'], 'd4e5f6...' => ['/path/x.log', '/path/y.log', '/path/z.log'] ]
4. 安全删除重复文件(保留首个,删除其余)
⚠️ 重要:删除前务必确认逻辑并建议先启用模拟模式
$deletedCount = 0;
foreach ($duplicates as $hash => $paths) {
// 保留第一个文件(通常作为原始源),其余标记为待删
$toDelete = array_slice($paths, 1); // 跳过索引 0
foreach ($toDelete as $file) {
if (unlink($file)) {
echo "✓ Deleted: $file\n";
$deletedCount++;
} else {
echo "✗ Failed to delete: $file (check permissions)\n";
}
}
}
echo "Total duplicates removed: $deletedCount\n";注意事项与最佳实践
-
路径安全:
$_GET['name']直接拼接存在路径遍历风险(如../etc/passwd),生产环境必须使用realpath()+dirname(__FILE__)白名单校验,或改用 POST + token 验证。 -
大文件处理:
hash_file()会加载整个文件进内存。对超大文件(>1GB),可考虑分块哈希或先比对文件大小再哈希(优化性能)。 -
原子性与日志:关键场景建议先将待删列表写入日志文件,人工复核后再执行
unlink();或使用事务式临时重命名+确认机制。 -
错误处理:始终检查
hash_file()返回值及unlink()结果,避免静默失败。
通过以上步骤,你不仅能精准定位内容级重复文件,还能以可控、可审计的方式完成清理,显著提升文件系统健康度与运维效率。



















