Beefy Boxes and Bandwidth Generously Provided by pair Networks
No such thing as a small change
 
PerlMonks  

About Tabbed Printing

by monkfan (Curate)
on Dec 10, 2005 at 14:19 UTC ( #515723=perlquestion: print w/replies, xml ) Need Help??

monkfan has asked for the wisdom of the Perl Monks concerning the following question:

Hi,
How can I do a very simple neat tabbed printing? My code below although already included tab (\t), it still doesn't follow my 'order'.
use Data::Dumper; my @aoa = ( [qw (GAL_up800.fasta 6 800 4.8)], [qw (hm01g.fasta 18 2008 36.144)], [qw (hm02r.fasta 9 1000 9)], [qw (train_muscle.fasta 7 50 0.35 )], ); #print Dumper \@aoa ; foreach my $aref (@aoa) { print "$aref->[0]\t\t $aref->[1]\t $aref->[2]\t $aref->[3]\n"; }
It doesn't print this format - especially the last line (the indentation starting from second column is not right):
GAL_up800.fasta 6 800 4.8 hm01g.fasta 18 2008 36.144 hm02r.fasta 9 1000 9 train_muscle.fasta 7 50 0.35
What is the standard practice for simple neat-printing like this? Is there any module that does this job?

Regards,
Edward

Replies are listed 'Best First'.
Re: About Tabbed Printing
by ikegami (Patriarch) on Dec 10, 2005 at 14:32 UTC
    printf and Perl formats are useful.
    foreach my $aref (@aoa) { printf("%-24s %7d %7d %f\n", @$aref); }

    If you search CPAN, I'm sure you'll find some module which automatically calculate how wide a column should be.

Re: About Tabbed Printing
by robin (Chaplain) on Dec 10, 2005 at 18:37 UTC
    The old-school solution is to use Perl formats. For your example, you could write:
    my @aoa = ( [qw (GAL_up800.fasta 6 800 4.8)], [qw (hm01g.fasta 18 2008 36.144)], [qw (hm02r.fasta 9 1000 9)], [qw (train_muscle.fasta 7 50 0.35 )], ); my $aref; # Variable must be visible to the format format STDOUT = @<<<<<<<<<<<<<<<<<<<<<< @<<<<<< @<<<<<< @<<<<<< @$aref . foreach $aref (@aoa) { write; }

    For a more contemporary solution, why not try Perl6::Form? It looks very nice from what I've seen.

      Caveat: Perl6::Form uses filters (by way of Perl6::Export) and requires Perl 5.8. Filters are generally seen as unfit for production code, and many people still use Perl 5.6.
        It's certainly true that Perl6::Form only works with Perl 5.8 and later, so you can't use it if you're still on 5.6.

        But I think your concern about source filtering is misplaced in this instance. Perl6::Form doesn't use a source filter on your code - it uses it on its own code. The problem with source filters that attempt to add syntax to Perl is that they will never parse the language completely accurately, and so will misbehave on certain code. (That's why Switch.pm is unreliable, for example.) In this case, the code that's being filtered is the source code of Perl6::Form, which obviously won't change, and has been verified to work with the Perl6::Export filter.

Re: About Tabbed Printing
by xdg (Monsignor) on Dec 10, 2005 at 19:25 UTC

    You might want to check out various table-generating modules. For example, I browsed a recent CPAN update to Text::TabularDisplay and it looks fairly nice. I'm sure there are others. That might be easier/nicer than messing with formats or other things.

    -xdg

    Code written by xdg and posted on PerlMonks is public domain. It is provided as is with no warranties, express or implied, of any kind. Posted code may not have been tested. Use of posted code is at your own risk.

Re: About Tabbed Printing
by TedPride (Priest) on Dec 10, 2005 at 16:46 UTC
    The following will do what you want. Just change the call to printspaced() so it passes whatever delimiter you want as the first argument.
    use strict; use warnings; chomp (my @data = <DATA>); $_ = [split / /] for @data; printspaced(' ', \@data); sub printspaced { my ($s, $d, @f, $f) = @_; push @f, '%-'.$_.'s' for widths($d); $f = join($s, @f)."\n"; printf($f, @$_) for @$d; } sub widths { my ($d, @r, $i) = $_[0]; for (@$d) { no warnings; for ($i = 0; $i <= $#$_; $i++) { $r[$i] = length($_->[$i]) if length($_->[$i]) > $r[$i]; } } return @r; } __DATA__ GAL_up800.fasta 6 800 4.8 hm01g.fasta 18 2008 36.144 hm02r.fasta 9 1000 9 train_muscle.fasta 7 50 0.35
Re: About Tabbed Printing
by turo (Friar) on Dec 12, 2005 at 00:48 UTC
    And what do you think about Text::Table (http://search.cpan.org/~anno/Text-Table-1.107/lib/Text/Table.pm)?
    I like very much the ``perl old-school technique'' showed by robin, but using this module is even more simple ^_^
    #!/usr/bin/perl -w use Text::Table; my @aoa = ( [qw (GAL_up800.fasta 6 800 4.8)], [qw (hm01g.fasta 18 2008 36.144)], [qw (hm02r.fasta 9 1000 9)], [qw (train_muscle.fasta 7 50 0.35 )], ); my $tb = Text::Table->new(); $tb->load(@aoa); print $tb;
    You create the object, load your table and print its out, the Text::Table will format and align the elements on the table for you ...
    GAL_up800.fasta 6 800 4.8 hm01g.fasta 18 2008 36.144 hm02r.fasta 9 1000 9 train_muscle.fasta 7 50 0.35
    Cool isn't it?

    perl -Te 'print map { chr((ord)-((10,20,2,7)$i++)) } split //,"turo"'
Re: About Tabbed Printing
by TedPride (Priest) on Dec 10, 2005 at 18:58 UTC
    Yes, but then you're back to the original problem of having to set the width of each field manually. And printf is neater.

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://515723]
Approved by Happy-the-monk
Front-paged by neversaint
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others wandering the Monastery: (3)
As of 2022-12-09 06:05 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found

    Notices?