2012-11-22 55 views
1

如何僅解析包含單詞QUERY的行? 我想:解析文件中只需要的行

my @strs = loadf('ck.txt');  

while(1) 
{ 
    my $str = shift @strs; 
    if(!$str) 
    { 
     exit; 
    } 
    if($str =~ /QUERY/) 
    { 
     ($cl) = $str =~ /QUERY: (.*?)/; 
     open F, ">>go.txt"; 
     print F $cl; 
     close F;  
    } 
} 




sub loadf { 
    open (F, "<".$_[0]) or erroropen($_[0]); 
    chomp(my @data = <F>); 
    close F; 
    return @data; 
} 

ck.txt:

22.11.2012 16:55:45 +02:00 
IP: 99.992.92.992 
QUERY: BANNER_LANG=ru; textext community-lang=ru 
REFERER: http:/site.ru/827 
AGENT: Opera/9.80 (Windows NT 6.0) Presto/2.12.388 Version/12.10 

22.11.2012 16:55:44 +02:00 
IP: 89.189.191.6 
QUERY: BANNER_LANG=ru; text; community-lang=ru 
REFERER: http:/site.ru/444 
AGENT: Opera/9.80 (Windows NT 5.1; U; ru) Presto/2.10.289 Version/12.00 

但它不工作= \

+0

「它不起作用「是一種流行的,但可悲的是不足以描述你的問題的方式。 – TLP

回答

0

要麼刪除?,使之貪婪或閉幕後添加$)

QUERY: (.*) 

QUERY: (.*?)$ 
1

你的問題是(.*?)?使匹配非貪婪,所以它會匹配儘可能少的字符,同時仍然滿足正則表達式。在這種情況下,這總是零個字符。

此外,您的代碼可以簡化爲:

use strict; 
use warnings; 

my @strs = ('BLAH', ' QUERY: foobarbaz', 'QUERY asdf');  

#open the file once: more efficient. 
open my $file, '>>', 'go.txt' or die "Can't open file: $!"; 
for my $str (@strs) 
{ 
    #Perform all matching logic in one go. 
    if($str =~ m/QUERY: (.*)/) 
    { 
     print {$file} $1; 
    } 
} 
close $file; 
0

你複雜的事情。你的問題可以用一行代碼來解決:

perl -nlwe 'print if /^QUERY/' query.txt >> go.txt 

您可以考慮從正則表達式清除管線錨^的開始,如果你的數據是不規則的。

如果你要刪除的字QUERY:您可以使用此一班輪:

perl -nlwe 'print if s/^QUERY:\s*//' query.txt >> go.txt 

這一個班輪的deparsed代碼(編輯爲簡單起見):