diff options
| author | Jörg Sommrey <28217714+jo-37@users.noreply.github.com> | 2022-05-24 14:22:52 +0200 |
|---|---|---|
| committer | Jörg Sommrey <28217714+jo-37@users.noreply.github.com> | 2022-05-27 18:01:13 +0200 |
| commit | 38fe9d67ea8576cc101c56d1672ae0f4be947ce3 (patch) | |
| tree | 98ac42ea06549c38c45a61ab3172156a11d23694 /challenge-166 | |
| parent | 780ce6107eca4fae3e52184a89a39bed8e45f6c0 (diff) | |
| download | perlweeklychallenge-club-38fe9d67ea8576cc101c56d1672ae0f4be947ce3.tar.gz perlweeklychallenge-club-38fe9d67ea8576cc101c56d1672ae0f4be947ce3.tar.bz2 perlweeklychallenge-club-38fe9d67ea8576cc101c56d1672ae0f4be947ce3.zip | |
Solution to task 2
Diffstat (limited to 'challenge-166')
| -rwxr-xr-x | challenge-166/jo-37/perl/ch-2.pl | 68 |
1 files changed, 68 insertions, 0 deletions
diff --git a/challenge-166/jo-37/perl/ch-2.pl b/challenge-166/jo-37/perl/ch-2.pl new file mode 100755 index 0000000000..3b395a8df2 --- /dev/null +++ b/challenge-166/jo-37/perl/ch-2.pl @@ -0,0 +1,68 @@ +#!/usr/bin/perl + +use v5.16; +use warnings; +use autodie; +use List::Util qw(max pairgrep); +use experimental 'signatures'; + + +die <<EOS unless @ARGV; +usage: $0 dir... + +dir... + Compare content of given directories + +EOS + + +### Input and Output + +print_diff(\@ARGV, dir_diff(@ARGV)); + + +### Implementation + +# Build a hash with the file names found in any directory as keys and an +# array indicating the files' presence within the directories. Files +# contained in all directories are filtered out. Equally named files +# and directories are regarded as different objects. File contents are +# not compared. +sub dir_diff (@dirs) { + my %files; + # Loop over the directories. + while (my ($i, $dir) = each @dirs) { + opendir(my $dh, $dir); + # Loop over the directory's files. + while (readdir $dh) { + # Append "/" to directories. + $_ .= '/' if -d "$dir/$_"; + # Set an indicator for the current directory. + $files{$_}[$i] = 1; + } + closedir $dh; + } + + # Exclude files that exist in all directories. + +{pairgrep {@dirs > grep $_, @$b} %files}; +} + +# Print the directory diff in a terse matrix format: "X" indicates the +# presence of a file in a directory. +sub print_diff ($dir, $diff) { + my $dlen = max map length, @$dir; + my $flen = max 0, map length, keys %$diff; + + # Table header + printf "%${flen}s" . (" | %${dlen}s" x @$dir) . "\n", + '', @$dir; + printf "%${flen}s" . ("-+-%${dlen}s" x @$dir) . "\n", + '-' x $flen, ('-' x $dlen) x @$dir; + + # Table rows + for my $file (sort keys %$diff) { + printf "%-${flen}s", $file; + printf " | %${dlen}s", 'X' x !!$diff->{$file}[$_] for 0 .. $#$dir; + print "\n"; + } +} |
