G'day soblanc,
It's not clear whether undef values have erroneously crept into your data and you want to fix that;
or if undef values are quite valid and you simply want to skip them when filtering.
You haven't shown how you create @matrix so some guesses are needed here.
The code below is effectively in two parts:
-
A variety of ways that undef values could have crept into your data.
This is by no means a complete list of possibilities.
It should give you hints as to what to look for when fixing the data.
-
How to skip undef values when filtering.
Based on your last post (Sort a matrix by row), and "my script handles millions of lines" (in this post)
it looks like you're dealing with biological data; accordingly, you'll want to pay attention to code efficiency —
not just for this small snippet but for your entire program.
grep EXPR, LIST (which I used) is faster than grep BLOCK LIST (which you used):
see grep.
You can test that for yourself with Benchmark.
#!/usr/bin/env perl
use v5.26.3;
use warnings;
my @matrix;
my ($col2, $col3) = qw{column2 column3};
my $keep_re = qr{1};
my $fmt = "%d: %-5s %s %s\n";
{
my $col1;
push @matrix, [$col1, $col2, $col3];
}
{
my $col1 = [];
push @matrix, [$col1->[0], $col2, $col3];
}
{
my @col1s;
my $elem1;
push @col1s, $elem1;
push @matrix, [$col1s[0], $col2, $col3];
}
{
my @col1s = (1);
pop @col1s;
push @matrix, [$col1s[0], $col2, $col3];
}
{
my @col1s = (2);
my $elem1;
unshift @col1s, $elem1;
push @matrix, [$col1s[0], $col2, $col3];
}
for (1, 2, 12, 100, 234) {
push @matrix, [$_, $col2, $col3];
}
say '*** Original:';
my @original = @matrix;
for (0 .. $#original) {
$original[$_][0] //= 'undef';
printf $fmt, $_, @{$original[$_]};
}
say '*** Filtered:';
my @filtered
= grep +(defined $_->[0] and $_->[0] =~ $keep_re), @matrix;
for (0 .. $#filtered) {
$filtered[$_][0] //= 'undef';
printf $fmt, $_, @{$filtered[$_]};
}
Output:
*** Original:
0: undef column2 column3
1: undef column2 column3
2: undef column2 column3
3: undef column2 column3
4: undef column2 column3
5: 1 column2 column3
6: 2 column2 column3
7: 12 column2 column3
8: 100 column2 column3
9: 234 column2 column3
*** Filtered:
0: 1 column2 column3
1: 12 column2 column3
2: 100 column2 column3
While I'm not advocating the use of "no warnings 'uninitialized';" in this instance,
I will point out that the effect of the warnings pragma is lexically scoped.
When it's appropriate, turn off warnings in as small a scope as possible.
use warnings;
...
# all warnings in effect here
{
no warnings 'XYZ';
# all warnings except XYZ in effect here
}
# all warnings in effect here
|