0

Perl プログラムで PDB データベースを一度に 1 ファイルずつソートできるようにしようとしています。私が必要としているのは、ファイルを読み取り、パターン マッチングを少し行い、結果に応じて、ファイル名を変更せずにファイルを適切なフォルダーに移動するプログラムです。これまでのところ、私はこれを思いつきました:

#!/usr/bin/perl
use File::Basename;

@files = <top8000/rands/*> ; 
$file = 0;
$count = 1; 
while ( open (FILE, $files[$file]) )
{
    while (  $FILEREAD = <FILE> ) 
    {
        if ( $FILEREAD =~ "pattern" ) 
        {
            $count++;        
        };
    };
    $string ="$files[$file]";
    $filename = fileparse($string);
    if ($count >=2 ) {
        rename ( $files[$file] , "top8000/randsort/$filename.txt" );
    };
    $count = 1;
    $file++;
};

ここでand変数myの前に使用することになっていることはわかっていますが、私のプログラムはそれで実行されず、それが何をするのかよくわかりません。それとは別に、自分のプログラムの何が問題なのかわかりません。助けていただければ幸いです。 $string$filename

4

1 に答える 1

1

まあ、あなたは自分で物事を複雑にしているようです。あなたの問題は、まだ読み取り用に開いているファイルの名前を変更しようとしていることにあると思います。原則として、次のように、すべてのファイル インタラクションの戻り値を常に確認する必要があります。

open my $fh, "<", $file or die "Cannot open file: $!";
rename $old, $new or die "Cannot rename: $!";

一般的に言えば、このようなエラーは致命的であると見なされることが多いためです。

いくつかの組み込み機能を使用することで、プログラムを大幅に簡素化できます。

use strict;
use warnings;  # always use these two
use File::Copy qw(move);

@ARGV = <top8000/rands/*.txt> unless @ARGV;  # default args    
my $outdir = "top8000/randsort";

while (<>) {           # read through the files
    if (/pattern/) {   # check each line
        close ARGV;    # close the file handle
        move $ARGV, $outdir or die "Cannot move $ARGV: $!";
    }
}

ご覧のとおり、File::Copyモジュールを使用するときにファイル名を指定する必要はありません。宛先アドレスがフォルダーの場合は、古い名前が使用されます。

ダイヤモンド オペレータを<>使用しています。これを使用すると、標準入力の STDIN ファイル ハンドルを使用するか、この場合は でスクリプトに引数として指定されたファイルを開いて読み取ります@ARGV。これは Perl であるため、必要なことを行うことができ、何もない場合はデフォルトの引数を入れるだけです。

カウントが 1 つ以上のヒットをチェックしたため、最初の一致でファイルを移動するのと事実上同じなので、そうしない理由はありません。最初にファイルを閉じてください。この場合のファイルハンドルはARGV. これにより、 の次のファイルにスキップすることもできます@ARGV。これは非常に便利です。ファイル名は に含まれており、これ以上操作する必要がないため、モジュール$ARGVは必要ありません。File::Basename

File::CopyPerl 5 のコア モジュールなので、インストールは不要です。

于 2013-06-11T10:52:00.707 に答える