【问题标题】:How can I compare two files and show differences in Perl?如何比较两个文件并在 Perl 中显示差异?
【发布时间】:2016-05-24 14:10:41
【问题描述】:

我正在尝试编写 Perl 脚本来比较 2 个文件的内容,以便列出所见的任何差异。尝试以下,但我不知道如何继续。请注意,以下只是脚本的一部分,因为我事先已对 2 个文件的内容进行了排序。提前致谢。

open (FILE1, "log") || die ("Can't open file log for reading") ;
open (FILE2, "master") || die ("Can't open file master for reading") ;

@file1 = <FILE1> ;
@file2 = <FILE2> ;

#$perlcompare = (compare('log','master')== 0) ;
#die ("Log and master files are equal and match.\n") ;

if (@file1 eq @file2) {

print "Log and master are equal and match.\n" ;
} else  ????????????

exit 0;

【问题讨论】:

  • 您要逐行比较文件并打印不匹配的行吗?如果您只想知道文件是否相同,您不能在操作系统中使用 diff 实用程序或 md5sum 吗?
  • @file1 eq @file2 仅检查它们是否具有相同的行数。 @file1 ~~ @file2 将比较内容。如果你使用 Text::Diff,正如思南回答的那样,你根本不需要做额外的检查。

标签: perl file diff


【解决方案1】:

如果您需要留在 Perl 中,File::Compare 只会比较文件。

为了显示差异,有Text::Diff

C:\Temp> cat file1
1
2
3
4
5
C:\Temp> cat file2
1
2
3
5
#!/usr/bin/env perl

use strict; use warnings;

use Text::Diff;

my $diffs = diff 'file1' => 'file2';

print $diffs;

输出

C:\Temp> t
--- file1 2011 年 11 月 18 日星期五 00:01:40
+++ 文件2 2011 年 11 月 18 日星期五 00:01:49
@@ -1,5 +1,4 @@
 1
 2
 3
-4
+5
-5

【讨论】:

  • 用户也要求显示差异,但该模块似乎不会这样做。
  • 感谢您指出这一点。不知何故,我第一次阅读这个问题时错过了它。
  • 感谢大家的回答,我尝试使用 diff 模块如下,虽然它确实比较了,但我希望输出只显示不匹配的东西,比如我想显示文件 1(日志)显示额外的项目或缺少与文件 2 相比的项目。我可以知道任何解决此问题的技巧吗?打开输出,“输出2”; $diffs = diff 'log' => 'list' ;打印输出 $diffs ;关闭输出;
【解决方案2】:

如果你可以使用 perl 以外的任何东西,我会推荐 diff(1) 或 comm(1)

comm -3 sorted-file-1 sorted-file-2

【讨论】:

  • 我有两个名为“log”和“master”的文件,尝试使用 --> comm -3 "log" "master" -2 但它标记我有错误。这个命令是否带有预定义的模块?
  • 我正在使用 if (@file1 eq @file2) { print "Log and master are equal and match.\n" ; } else XXXXX 在我的脚本中,实际上当2个文件匹配时它可以正确执行。我假设当不匹配时“eq”命令将返回“0”。所以,当条件为“0”时考虑设置其他,然后它将继续获取不匹配的字符串......但不知道如何继续。另外,想知道“eq”命令是否正在检查整个文档,当它发现第一个不匹配时它会停止。
  • 你的错误是什么?正如我在archlinux上看到的那样,comm带有coreutils
  • @Grace eq 不会比较数组的内容。尝试 perl -we '@a=(1,2); @b=(3,4); print "yes" if @a eq @b;' eq 将数组置于标量上下文中,这意味着比较它们的大小,而不是它们的内容。但是,您 可以 将数组与智能匹配进行比较,例如@a ~~ @b.
【解决方案3】:
#!/usr/bin/perl
use strict;
use warnings;
use List::Compare;

open (my $log, "<", "log") or die $!;
open (my $master, "<", "master") or die $!;
my @content_log=<$log>;
my @content_master=<$master>;

my $lc = List::Compare->new(\@content_log, \@content_master);    
my @intersection = $lc->get_intersection;
my @firstonly = $lc->get_unique;
my @secondonly = $lc->get_complement;

print "Common Items:\n"."@intersection"."\n";
print "Items Only in First List:\n"."@firstonly"."\n";
print "Items Only in Second List:\n"."@secondonly"."\n";

print "log\n", $lc->get_unique,"\n"; 
print "master\n", $lc->get_complement,"\n"; 

close $log;
close $master;

【讨论】:

    猜你喜欢
    • 2015-08-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-06-17
    • 2021-12-11
    • 2014-06-08
    • 2017-06-06
    相关资源
    最近更新 更多