I need to compare two array and get differences.
Background:
1st array will list out files in folder.
2nd array will read the content of a file and stored in array.
The output of 1st array will be
a
b
c
d
e
The output of 2nd array will be
a
b
c
e
How I can compare those 2 array that get differences? The finale output that I want is
d
Here is the code:
#!/usr/bin/perl
use strict;
use warnings;
my $list = "experiment.sv";
my $path = "../../../folder1/";
my $filelist;
open ( OUTFILE, ">output.txt" );
main ();
close OUTFILE;
sub main {
my @array1;
opendir ( DIR, $path ) || die "Error in opening dir $path\n";
while ( $filelist = readdir (DIR) ) {
next if ( $filelist =~ s/\.//g); #/
push @array1, $filelist;
}
closedir(DIR);
my @array2;
open( my $fh, "<", "$path/$list") or die "Failed to open file: $!\n";
while(<$fh>) {
push @array2, $_;
}
close $fh;
my @result;
foreach my $array2 (@array2) {
foreach my $array1 (@array1) {
if ($array1 !~ /$array2/ ) {
push @result, "$array1\n";
}
}
}
print OUTFILE "",@result;
}
There are a few ways to do this, also depending on what exactly is needed.
Using an ancillary hash for each array, to reduce the existence check to a lookup
use warnings;
use strict;
use feature 'say';
sub diff_arys {
my ($ra1, $ra2) = @_;
my %in_a1 = map { $_ => 1 } @$ra1;
my %in_a2 = map { $_ => 1 } @$ra2;
my @not_in_one = grep { not exists $in_a1{$_} } @$ra2;
my @not_in_two = grep { not exists $in_a2{$_} } @$ra1;
return (@not_in_one ? \@not_in_one : undef),
(@not_in_two ? \@not_in_two : undef);
}
my @ary1 = 'a'..'e'; # a,b,c,d,e
my @ary2 = ('a'..'d', 'z'); # a,b,c,d, z
my ($not_in_one, $not_in_two) = diff_arys(\@ary1, \@ary2);
say "@$not_in_one" if $not_in_one;
say "@$not_in_two" if $not_in_two;
Prints
z e
This finds difference both ways, elements in one array but not in the other. If you know for fact that you only need it for one "direction," to identify things that are in the first array but not in the second (as it seems from the question), then adjust the sub so to only get needed return. Then there's less code, and you can just return the array (so, a list or empty)
Note the choice for the interface: Return undef
if no difference is found, an arrayref otherwise.
There are good modules for this kind of work. A rather comprehensive one is List::Compare. There are also Array::Utils and Array::Compare, and yet more. And then there are more complex tools that can also be used for this, like Algorithm::Diff.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With