免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 1884 | 回复: 6
打印 上一主题 下一主题

闲时无聊,自己写的查找相同文件的脚本 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2010-03-27 10:03 |只看该作者 |倒序浏览
本帖最后由 kzled 于 2010-03-31 22:25 编辑
  1. use strict;
  2. use warnings;
  3. use Cwd;
  4. use File::Basename;
  5. use Digest::MD5;

  6. my $path = shift || getcwd();

  7. if ( ! -d $path ){
  8.         $0 = basename($0);
  9.         print <<HELP;
  10. USAGE:
  11. \tperl $0 path

  12. EXAMPLE:
  13.         perl $0 d:\\
  14.         perl $0 d:\\docs
  15.        
  16. For more please contact me by liyuncn\@yahoo.com
  17. HELP

  18.         exit;
  19. }

  20. # use to store fileNames and md5s, keys are md5s, values are filenames
  21. my %duplicates;

  22. &read($path);
  23. &output;


  24. sub read{
  25.         my $dir = shift;
  26.         my (@dirs, $size, $file);
  27.        
  28.         opendir (DIR, $dir) or die "Failed to open $dir: $!\n";
  29.        
  30.         LOOP:
  31.         while ( $file = readdir(DIR) ){
  32.                
  33.                 # Skipped system files start name with ...
  34.                 next if ($file =~ /^\./);
  35.                
  36.                 if ( $dir =~ m/\\$/ ){
  37.                         $file = $dir.$file;
  38.                 }else{
  39.                         $file = $dir."\\".$file;
  40.                 }
  41.                
  42.                 # Put dirs into an array, to recursive call read subroutine
  43.                 if ( -d $file ){
  44.                         push @dirs, $file;
  45.                 }else{
  46.                         # Got files size and put them in hash as key
  47.                         $size = -s $file;
  48.                        
  49.                         # Using $size as key, if $size exisit, => next steps
  50.                         if (exists $duplicates{$size}){
  51.                                 my $md5;
  52.                                 my @md5s;
  53.                                
  54.                                 foreach ($file, $duplicates{$size}[0]){
  55.                                        
  56.                                         open( FILE, $_ )  or die "Failed to open $file: $!\n";
  57.                                         binmode(FILE);
  58.                        
  59.                                         # Get md5 value from files, make it keys of %duplicates
  60.                                         $md5 = Digest::MD5->new->addfile(*FILE)->hexdigest;
  61.                                        
  62.                                         push @md5s, $md5;
  63.                                         close FILE;
  64.                                 }
  65.                                
  66.                                 push ( @{$duplicates{$size}}, $file ) if ( $md5s[0] eq $md5s[1]);
  67.                                
  68.                                 next;
  69.                         }
  70.                        
  71.                         $duplicates{$size} = [$file];
  72.                 }
  73.         }
  74.        
  75.         # Close dir
  76.         closedir DIR or die "Error happen at closing dir: $!\n";
  77.        
  78.         # Recursive call subroutine read
  79.         foreach (@dirs){
  80.                 &read($_);
  81.         }
  82. }

  83. sub output{
  84.         my %dups = %duplicates;
  85.        
  86.         foreach my $key ( keys %dups ){
  87.                
  88.                 # For each values array in $Dups hash, if more than 1 files, print them out
  89.                 if ($#{$dups{$key}}> 0){
  90.                         print "Duplicated files found:\n";
  91.                         print "-------------------------------------------------\n";
  92.                        
  93.                         # Print file details..
  94.                         foreach (@{$dups{$key}}){
  95.                                 print $_."\n";
  96.                         }
  97.                         print "-------------------------------------------------\n";
  98.                 }
  99.         }
  100. }


复制代码

论坛徽章:
0
2 [报告]
发表于 2010-03-27 10:23 |只看该作者
不错的

论坛徽章:
0
3 [报告]
发表于 2010-03-27 10:31 |只看该作者
{:3_190:}我是想抛砖引玉的。。。

论坛徽章:
0
4 [报告]
发表于 2010-03-27 19:01 |只看该作者
好似好长··

论坛徽章:
0
5 [报告]
发表于 2010-03-27 21:22 |只看该作者
本帖最后由 kzled 于 2010-03-31 22:26 编辑

长?才一百行?
----

论坛徽章:
0
6 [报告]
发表于 2010-03-28 09:11 |只看该作者
回复 5# kzled
  1. if ( $file =~ /\.doc$/ || $file =~ /\.xls$/ || $file =~ /\.txt$/ || $file =~ /\.ppt$/ || $file =~ /\.conf/){
  2.                                  $type = "docs";
  3.                          }
复制代码
这样写不累么   呵呵
换成  $file =~ /\.(doc|xls|txt)$/    这样
或者  放到hash里  然后 print $hash->{$exe} if(exists $hash->{$exe})
应该可以少写一些

论坛徽章:
0
7 [报告]
发表于 2010-03-28 11:43 |只看该作者
回复 6# guap514


     嗯,谢谢,提醒,这样可以省了不少代码,写这个脚本的时候,压根没怎么看正则表达式,所以现在代码看起来相当难看。。。呵呵
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP