Эта часть кода не имеет смысла:
while ( my $filelist = readdir (DIR) ) {
...
foreach $_ (@not_included){
chomp $_;
my $not_included = "$_";
if ( $filelist eq $not_included ){
next;
} # (1)
push @unsort_output, $filelist; # (2)
}
Этот код содержит три открывающие скобки ({
), но только две закрывающие скобки (}
). Если вы попытаетесь запустить свой код как есть, произойдет сбой с синтаксической ошибкой.
Линия push
(отмечена (2)
) является частью цикла foreach
, но с отступом, как если бы она находилась снаружи. Либо следует добавить отступ больше (для выравнивания с (1)
), либо вам нужно добавить }
перед ним. Ни одна из альтернатив не имеет большого смысла:
- Если
push
находится вне цикла foreach
, то оператор next
(и весь цикл foreach
) не действует. Это может быть просто удалено.
- Если
push
находится внутри цикла foreach
, то каждая запись в каталоге ($filelist
) будет нажиматься несколько раз, по одному для каждой строки в @not_included
(за исключением имен, перечисленных где-то в @not_included
; те будут толкаться в один раз меньше).
Есть несколько других проблем. Например:
$filelist =~ s/\.//g
удаляет все точки из имени файла, преобразуя, например, file_c.sv
в file_csv
. Это означает, что он никогда не будет совпадать с NOT_INCLUDED=file_c.sv
во входном файле.
- Хуже того, часть
next if s///
означает, что цикл пропускает все файлы, имена которых содержат точки, такие как Output1.sv
или Output2.sv
.
- Результаты печатаются без разделителей, поэтому вы получите что-то вроде
Folder1Folder1Folder1Folder2Folder2Folder2file_afile_afile_bfile_b
в OUTPUT.txt
.
- Глобальные переменные используются без причины, например
INFILE
и DIR
.
Вот как я бы структурировал код:
#!/usr/intel/perl
use strict;
use warnings;
my $input_file = 'INPUT.txt';
my %is_blacklisted;
{
open my $fh, '<', $input_file or die "$0: $input_file: $!\n";
while (my $line = readline $fh) {
chomp $line;
if ($line =~ s!\ANOT_INCLUDED=!!) {
$is_blacklisted{$line} = 1;
}
}
}
my $path = 'experiment';
my @results;
{
opendir my $dh, $path or die "$0: $path: $!\n";
while (my $entry = readdir $dh) {
next
if $entry eq '.' || $entry eq '..'
|| $entry =~ /\.list\z/
|| $entry =~ /\.swp\z/
|| $is_blacklisted{$entry};
push @results, $entry;
}
}
@results = sort @results;
my $output_file = 'OUTPUT.txt';
{
open my $fh, '>', $output_file or die "$0: $output_file: $!\n";
for my $result (@results) {
print $fh "$result\n";
}
}
Содержимое INPUT.txt
(точнее, части после NOT_INCLUDED=
) считывается в хеш (%is_blacklisted
). Это позволяет легко искать записи.
Затем мы обрабатываем записи каталога. Мы пропускаем .
и ..
(я полагаю, они вам не нужны), а также все файлы, заканчивающиеся *.list
или *.swp
(что было в вашем исходном коде). Мы также пропускаем любой файл, который находится в черном списке, т. Е. Был указан как исключенный в INPUT.txt
. Остальные записи собраны в @results
.
Мы сортируем наши результаты и записываем их в OUTPUT.txt
, по одной записи в строке.