0

多くの値のセットで構成されるファイルがあります。REGEX が見つかったら、ファイル内で一致する必要な行を抽出しようとしています。ファイル.txt

    ...... 
    ......
    TRIP (
            ?name           "model"
            ?prompt         "Model name"
            ?defamount       "USD100"
            ?type           "adventure"
            ?display        "no"
            ?photos       "800"
               )
    TRIP (
            ?name           "macro"
            ?prompt         "macro model name"
            ?defamount       "USD500"
            ?type           "adventure"
            ?display        "no"
            ?photos       "1200"
            )
      TRIP( 
            ?name           "description"
            ?prompt         "description"
            ?defamount       "USD400"
            ?type           "historical"
            ?display        "yes"
            ?photos       "900"
             )
            .......
........
.....
.......
......

「名前とモデル」、「名前と説明」の行を抽出したいこれらの行とともに、「名前とモデル」、「名前と説明」の行が一致したら、最初の「デファマウント」を抽出したい。ループで試しましたが、成功しませんでした

use strict;
open FILE, "<File.txt";
open FILE2, ">>data1.l";

while (my $string = <FILE>) {

    if ($string =~ m/^ CELL/ig) {

        print FILE2 $string;
    }
    elsif ($string =~ m/"model"/i) {

        print FILE2 $string;
    }
    elsif ($string =~ m/defamount/o) {

        print FILE2 $string;
    }
    elsif($string =~ m/"description"/i) {

        print FILE2 $string;
    }
    elsif($string =~ m/defamount/o) {

        print FILE2 $string;
    }
}
close FILE;
close FILE2; 

これにより、ファイルからすべての「defamount」行が得られますが、上記の正規表現に一致した後の最初のdefamountだけが必要です

4

1 に答える 1

1

これらのif...elsif構造のそれぞれは、入力のすべての行で計算されます。それらを行のグループとして扱う必要があるため、行がすでに一致しているかどうかを追跡して、これが保持するグループであるかどうかを判断します。

プログラムを完全に書き直さずに、次のようなことをする必要があります。

my $keep = 0;

while(my $string = <FILE>){
    if ($string =~ m/name\s+/){ #matches name, start of new group
        if ($string =~ m/"(model|description)"/){ # keep this group
            $keep = 1;
            print FILE2 $string;
        } else { #discard this group
            $keep = 0;
        }
    }
    if ($string =~ m/defamount/ && $keep){ #only print if in a 'keep' block
        print FILE2 $string;
    }
}

正直なところ、ゼロから始める場合は、これをまったく別の方法で記述します。それはあなたがそこで行っているかなり農業的なperlです。しかし、うまくいけば、私が書いたものの論理があなたが始めるのを助けるでしょう。

于 2012-09-10T02:51:46.680 に答える