あなたはそれが等しくなることを意味している、あなたの内側のループでmy $line
を再宣言しています。
Use of uninitialized value in pattern match (m//) at ...
私はあなたが警告を使用していない疑いがあるになり、非常に悪い考えです:あなたはuse warnings
を使用していた場合は、エラーを得ているでしょう。
また、値を@array
に読み込むと最後に改行が追加されるため、DATファイルで\n
で終わる文字列を検索しているため、必要でない可能性があります。例えば。 foo\n
の場合は、foo bar baz
と一致しません。
それに対する解決策は、あなたのデータをchomp
することです:
chomp(my @array = <TXT>);
はい、あなたは、配列をムシャムシャ食べることができ、あなたは配列に、このようにファイル全体を割り当てることができます。
スクリプトを少し改善することができます。実際に何かのインデックスを使用する必要がない限り、配列インデックスを使用してループするのは非常に不要です。 \Q
を使用して
use strict;
use warnings; # ALWAYS use these!
use autodie; # handles the open statements for convenience
my $source = "/KEYS.txt";
my $data= "/claims.dat";
open $txt, '<', $source;
chomp(my @array = <$txt>);
close $txt;
open my $dat, '<', $data; # use three argument open and lexical file handle
open my $log, '>>', "/output.log";
while (<$dat>) { # using $_ for convenience
for my $word (@array) {
if (/\Q$word/i) { # adding /i modifier to match case insensitively
print $log $line; # also adding \Q to match literal strings
}
}
は、あなたのKEYS.txtファイルが含まれているものに応じて、非常に重要であるかもしれません。正規表現のメタ文字は、文字通り一致すると予想される場合、微妙な不一致を引き起こす可能性があります。例えば。 foo?
などの単語がある場合、正規表現/foo?/
はfoo
に一致しますが、for
にも一致します。
また、部分一致を許可するかどうかを決めることもできます。例えば。 /foo/
もfootball
と一致します。
/\b\Q$word\E\b/i
あなたは\Q .. \E
シーケンス外にそれらを配置する必要があります、または彼らは文字通りに解釈されます。それを克服するために、一つの方法は、単語境界エスケープ文字を使用することです。
ETA: Tchristが指摘しBorodinが示唆するように、すべての単語を含む正規表現を構築すると、重複する行が保存されます。例えば。あなたは言葉"foo"
、"bar"
と"baz"
、そしてあなたは、この行が一致する各単語のために一回、3回印刷になるだろうfoo bar baz
ラインを持っている場合。
これは後で、データを適切な方法で削除することで修正される可能性があります。あなただけがあなたのデータを知っており、これが問題であるかどうかはわかりません。パフォーマンス上の理由から、このような長い正規表現をコンパイルすることを躊躇しますが、それを試して、それがあなたのために働くかどうかを確認することができます。
出典
2012-03-22 18:48:59
TLP
、あなたはおそらく 'grep'(LINUX/UNIX版ではなく、Perlを)使用することができます。例えば。 'grep -f /KEYS.txt/claims.dat'です。 – TLP
KEYS.txtの文字列が固定されているのか、それとも正規表現ですか?もしそれらが修正されていれば、 'grep -F -f KEYS.txt claims.dat'でスピードアップします。 Perlコードはマッチ演算子の代わりに['index'](http://p3rl.org/index)関数を使用します。 – daxim
KEYS.txtでは、実際には9桁です。他のポスターように102361550と481543095など – cluckinchicken