2011-08-16 36 views
0

我有两个名称不匹配的图像目录,但主要是匹配的图像。如何按文件大小匹配文件并进行相应的重命名?

Dir 1  Size | Dir 2     Size 
--------------------------------------------------- 
img1.jpg 508960 | a_image_name.jpg  1038644 
img2.jpg 811430 | another_image_name.jpg 396240 
...   ... | ...     ... 
img1000.jpg 602583 | image_name.jpg   811430 
...   ... | 
img2000.jpg 396240 | 

第一个目录有更多的图像,但名称有误。第二个目录具有正确的名称,但不对应于第一个目录。

我想通过比较文件大小(或其他方式)与Dir 2来重命名Dir 1中的文件。在上面的示例中,img2.jpg将被重命名为image_name.jpg,因为它们都具有相同的文件大小。

您能否指点我正确的方向?

最好通过应用程序(Mac),shell或php的方式。

回答

3

也许这会更明智地使用文件的散列,而不是使用文件大小?

简而言之:使用glob(),获取dir1中的文件列表,迭代,创建md5-hash(md5()+ file_get_contents()),将数组存储在数组中,并使用散列作为键和文件名作为值。 为dir2做同样的事情。

迭代阵列1,如果在数组2重命名文件中存在具有相同散列的条目

代码将是这样的:(未经检验,未优化)

$dir1 = array(); 
$dir2 = array(); 

// get hashes for dir1 
foreach(glob('/path/to/dir1/*.jpg') as $file) { 
$hash = md5(file_get_contents($file)); 
$dir1[ $hash ] = $file; 
} 

// repeat for dir2 ... 

foreach($dir1 as $hash => $file1) { 
if(array_key_exists($hash, $dir2)) { 
    rename($file1, $dir2[ $hash ]); 
} 
} 
+1

这是一个很好的答案,但是,你可以使用md5_file($文件),而不是MD5(的file_get_contents($文件)) – Landon

+0

我以为这存在,但说实话,我是懒得寻找到手动;)顺便说一句,当然没有必要建立2个数组 – wonk0

2

这里是我的解决方案,它重命名文件在dir1中根据文件大小。

DIR1的内容:

-rw-r--r-- 1 haiv staff 10 Aug 16 13:18 file1.txt 
-rw-r--r-- 1 haiv staff 20 Aug 16 13:18 file2.txt 
-rw-r--r-- 1 haiv staff 30 Aug 16 13:18 file3.txt 
-rw-r--r-- 1 haiv staff 205 Aug 16 13:18 file4.txt 

(注:第五列存储的文件大小。)和DIR2的内容:

-rw-r--r-- 1 haiv staff 30 Aug 16 13:18 doc.txt 
-rw-r--r-- 1 haiv staff 205 Aug 16 13:18 dopey.txt 
-rw-r--r-- 1 haiv staff 20 Aug 16 13:18 grumpy.txt 
-rw-r--r-- 1 haiv staff 10 Aug 16 13:18 happy.txt 

创建一个文件调用〜/ rename.awk(是的从主目录,以避免污染要么DIR1或DIR2):

/^total/ {next} # Skip the first line (which contains the total, of ls -l) 

{ 
    if (name[$5] == "") { 
     name[$5] = $NF 
     print "# File of size", $5, "should be named", $NF 
    } else { 
     printf "mv '%s' '%s'\n", $NF, name[$5] 
    } 
} 

现在,cd到DIR1(如果你想重命名Dir1中的文件),并发出以下命令:

$ awk -f ~/rename.awk <(ls -l ../dir2) <(ls -l) 

输出:

# File of size 30 should be named doc.txt 
# File of size 205 should be named dopey.txt 
# File of size 20 should be named grumpy.txt 
# File of size 10 should be named happy.txt 
mv 'file1.txt' 'happy.txt' 
mv 'file2.txt' 'grumpy.txt' 
mv 'file3.txt' 'doc.txt' 
mv 'file4.txt' 'dopey.txt' 

一旦你对结果满意,管上面的命令SH执行的更改:

$ awk -f ~/rename.awk <(ls -l ../dir2) <(ls -l) | sh 

注:

  1. 没有保障针对相同大小的文件。为此,wonk0提供的MD5解决方案效果更好。
  2. 请在提交之前检查输出。更改是永久性的。
相关问题