Hello zw, and welcome to the Monastery!
First, there is a right brace (curly bracket) missing, but that’s hard to see because of the way the code is formatted. A little reformatting —
use strict;
use warnings;
my $filename = 'gff.annotated.gtf';
open(my $fh, '<:encoding(UTF-8)', $filename) or die "Can't open $filen
+ame: $!";
my @transcript_id = ();
my @lines = <$fh>;
foreach my $lines (@lines)
{
my @column= split /\t/, $lines;
foreach $element (@column)
{
if ($element[16] eq '"u"' || '"x"' || '"i"' || '"s"')
{
push @transcript_id, $element[10];
}
}
print @transcript_id;
— and the missing brace is easily seen.
Second, you have use strict (good!), so $element needs to be declared with my:
foreach my $element (@column)
# ^^
Third, $element is a scalar variable, which on each iteration of the loop holds a single element of the @column array. But the expressions $element[16] and $element[10] reference an entirely different variable, an array named @element which you haven’t declared. In the case of $element[16], you probably just want to use $element. In the case of $element[10], I’m not sure what you want to do; maybe you meant $column[10]?
Fourth, Perl syntax requires that you make each comparison separately:
if ($element eq 'u' ||
$element eq 'x' ||
$element eq 'i' ||
$element eq 's')
{
push @transcript_id, $column[10];
}
Fifth, note that in the above snippet I have removed the extra quotation marks. Your problem description implies that you want to test for equality with the character u, not with the 3-character string "u" as you have in your code.
Sixth (and finally!), I think the logic of your inner foreach loop is questionable. Do you want to push to @transcript_id on each match in the line, or only once per line if a match is found? If the latter, you need to break out of the loop after the first match:
foreach $element (@column)
{
if ($element eq 'u' ||
$element eq 'x' ||
$element eq 'i' ||
$element eq 's')
{
push @transcript_id, $column[10];
last;
}
}
Hope that helps,
|