Thanks for spotting that! I tested it on the unique basenames case, not the case where pathnames differ only. Here's the corrected code:
#!/usr/bin/perl
# COLUMNS - Copyright (C) 2008 Xenoscience, Inc. - Released under GPL
+v3
# SSF 101808 - display files in columns side-by-side
use integer;
use strict;
use Getopt::Std;
use Term::Size 'chars';
my (%opts);
my ($cols,$rows)=chars;
getopts('d:htw:',\%opts);
unless (@ARGV or $opts{h}) {
print <<EOT;
Usage: columns [-d delimeter] [-h] [-w width] file file ...
Print files in properly spaced columns for the terminal width
-d C Delimiter between columns (defaults to spaces)
-h This help display
-t Display file names as titles (base names only if all unique
+)
-w N Assume N character width per line
EOT
exit 1;
}
$opts{d}||=' ';
$opts{w}||=$cols;
$cols=$opts{w};
my (@cols,$arr,$col,$row,$wd,$file,$len,$line,$maxrow,$spacer,
@titles,%titles);
for $file (@ARGV) {
$col=get_basename($file);
push @titles,$col;
$titles{$col}++;
$arr=[];
open(FILE,$file) || die "$file: $!";
while (<FILE>) {
chomp;
push @$arr,$_;
$len=length($_);
$wd=$len if $len>$wd;
}
close FILE;
$maxrow=scalar @$arr if $maxrow<scalar @$arr;
push @cols,$arr;
}
# compute spacer
$spacer=($cols/@cols)-1;
$wd=$spacer if $spacer>$wd;
$spacer=($cols/$wd);
--$spacer while ($spacer>0 and @cols*($wd+$spacer)-$spacer>$cols);
$spacer=$opts{d} x $spacer;
# titles
if ($opts{t}) {
# determine if titles can have pathnames chopped off
if (scalar @titles > scalar keys %titles) { # some same names
@titles=@ARGV;
}
$col=scalar @cols;
for $file (@titles) {
$line=(' ' x ($wd/2-length($file)/2)).$file;
print $line.(' ' x ($wd-length($line)));
--$col;
print $spacer if $col;
}
print "\n";
$col=scalar @cols;
for $file (@titles) {
print '=' x $wd;
--$col;
print $spacer if $col;
}
print "\n";
}
# content
for ($row=0; $row<$maxrow; ++$row) {
$col=scalar @cols;
for $arr (@cols) {
$line=$arr->[$row];
print $line.(' ' x ($wd-length($line)));
--$col;
print $spacer if $col;
}
print "\n";
}
exit;
sub get_basename { # extract basename from url or path
my $path=shift;
my $i=rindex($path,'/');
$i>-1 ? substr($path,$i+1) : $path;
}
|