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

I'm loading and printing tab-delimited files in my perl script. However the last column of my input file ($table1) is empty and I don't want to print this in my output file ($table3). How and where should I do this? After the 'open' or at the end in the 'print $table3'? This is part of my script (... denotes code not important for this question)

#! /usr/bin/perl use strict; use warnings; use Data::Dumper; local $Data::Dumper::Useqq = 1; use Getopt::Long qw(GetOptions);; ... open(my $table1,'<', $input) or die "$! - [$input]"; #input file open(my $table3, '+>', $output) || die ("Can't write new file: $!"); # +output file ... chomp( my @header_for_table1 = split /\t/, <$table1> ); print $table3 join "\t", @header_for_table1, "name1", "name2", "\n"; { no warnings 'uninitialized'; while(<$table1>){ chomp; my %row; @row{@header_for_table1} = split /\t/; print $table3 join ( "\t", @row{@header_for_table1}, @{ $lookup{ ... } // [ "", "" ] }), "\n"; } }

Replies are listed 'Best First'.
Re: remove last column of tab-delimited file
by Lotus1 (Vicar) on Jul 22, 2016 at 19:13 UTC

    This is nit-picky, but since you asked...

    chomp( my @header_for_table1 = split /\t/, <$table1> );

    That line is passing an array to chomp() which means it chomps every element. Only the last element will possibly have a newline character. If you split it into two lines it doesn't look as nice but is better Perl. It would have to be a large array before it would make any difference, hence the nit pick comment.

    chomp( my $line = <$table1> ); my @header_for_table1 = split /\t/, $line;

    Now that I think about it, you are going to discard the final element anyway so you don't need the chomp.

Re: remove last column of tab-delimited file
by kroach (Pilgrim) on Jul 22, 2016 at 17:57 UTC
    You can remove the last element of @header_for_table1 before reading the rest of $table1. This way, when you assign split to the hash slice of %row, the last element will be ignored.
      Would something like this work then?
      chomp( my @header_for_table1 = split /\t/, <$table1> ); @new_header_for_table1 = pop(@header_for_table1); print $table3 join "\t", @new_header_for_table1, "name1", "name2", "\n +";

        No need to assign the pop operation to anything since you want to throw it away. Just:

        pop(@header_for_table1);

        EDIT:

        To clarify, pop will alter the array you are using it on by removing the last element. It returns the last element that is removed, not all the remaining elements excluding the last element removed. So the code you showed would create a new array with just one element, the last element of the original array you wanted to discard. That's not what you want.

        I love it when things get difficult; after all, difficult pays the mortgage. - Dr. Keith Whites
        I hate it when things get difficult, so I'll just sell my house and rent cheap instead. - perldigious

        Why don't you try it instead of asking? ;)

        I would use splice @header_for_table1, -1 without assignment, as splice returns what it has removed from an array. Likewise pop cuts the last element off an array and returns it, but in contrary what you want is all items but the last, don't you?

        UPDATE: pop() without assignment is the same like splice(@array, -1), yeah.