2012-03-02 7 views
1

値が4行以上連続している場合(col1の値が同じ場合)、すべての行(4つ以上の行を印刷する必要があります)を出力する必要があります。連続値の抽出とすべての行の印刷

col1の値が等しく、col2とcol3の値が次の4行以上連続して連続している場合は、それらの行を返します。行のcol3の値は、次の行のcol2の値と等しいか、または100までしか小さくすることはできません。

ここで、連続とは1行(1行のcol3-col2)を意味するものではありません。これは、次の行のcol2値と比較して、行のcol3値を意味します。

私のファイルがある - >

 
A 0 100 
A1 0 100 
A1 100 200 
A1 200 300 
A1 400 500 
A1 500 600 
A1 600 700 
A1 700 800 
A1 1600 1700 
A2 100 200 
A2 200 300 
A2 400 500 
A2 500 600 
A2 600 700 
A3 800 900 

所望の出力は - >

 
A1 0 100 
A1 100 200 
A1 200 300 
A1 400 500 
A1 500 600 
A1 600 700 
A1 700 800 
A2 100 200 
A2 200 300 
A2 400 500 
A2 500 600 
A2 600 700

ここで1以上の例がある - >私の入力ファイル - >

 
A 0 100 
A1 0 100 
A1 100 200 
A1 200 300 
A1 500 600 
A1 600 700 
A1 700 800 
A1 1600 1700 
A2 100 200 
A2 200 300 
A2 400 500 
A3 800 900 

出力 - >

"No lines continuou 「s」。

出力がありません。次の行と比較すると、同じcol1値を持ち、col3値が100以下でなければならないので、出力はありません。

は、これまでのところ私はこれを試みたが、動作していない - >

use strict; 
use warnings; 

*ARGV or die "No input file specified"; 
open *first, '<',$ARGV[0] or die "Unable to open input file: $!"; 
my @data; 
while (<first>) { 

    if (not @data) { 
    @data = split; 
    next; 
    } 

    my @new = split /\s+/; 

    if ($new[0] eq $data[0] and $new[1] <= $data[2]+ 100) { 
    $data[2] = $new[2]; 
      if ($data[2] - $data[1] >= 500){ 
      print join("\t", @new), "\n"; 
      } 
    } 

    else { 
    @data = @new; 
    } 
} 

すべてのヘルプしてください。

+0

* *、あなたが継続的に何を意味するのです "COL2とCOL3の値は、(連続番号のように)連続して行っていますか"?私は何が連続しているのか分からない。 – Qtax

+1

@ Qtax:col3が、例えば100である1行(行)を考えてください。次に、次の行(行)のcol2も100(または200)でなければなりません。このことが5行連続して起こる場合は、それらの5行を印刷します。 – Vikas

+1

M42の答えはあなたに当てはまるはずです。 – Qtax

答えて

2

方法について:

#!/usr/bin/perl 
use strict; 
use warnings; 
use Data::Dump qw(dump); 
use 5.010; 

$_ = <DATA>; 
chomp; 
my ($p_key, $p_col1, $p_col2) = split; 
my @result = ($_); 
open my $fh, '>', 'path/to/output_file' or die "unable to open file:$!"; 
while(<DATA>) { 
    chomp; 
    my ($key, $col1, $col2) = split; 
    if ($key eq $p_key) { 
     if ($col1 <= $p_col2+100) { 
      push @result, $_; 
     } else { 
      print_to_file($fh, \@result) if (@result > 3); 
      @result =(); 
     } 
    } else { 
     print_to_file($fh, \@result) if (@result > 3); 
     @result = ($_); 
    } 
    ($p_key, $p_col2) = ($key, $col2); 
} 
print_to_file($fh, \@result) if (@result > 3); 

sub print_to_file { 
    my $fh = shift; 
    my $res = shift; 
    while(@$res) { 
     print $fh, $_, "\n"; 
    } 
} 
__DATA__ 
A 0 100 
A1 0 100 
A1 100 200 
A1 200 300 
A1 400 500 
A1 500 600 
A1 600 700 
A1 700 800 
A1 1600 1700 
A2 100 200 
A2 200 300 
A2 400 500 
A2 500 600 
A2 600 700 
A3 800 900 

出力:

(
    "A1 0 100", 
    "A1 100 200", 
    "A1 200 300", 
    "A1 400 500", 
    "A1 500 600", 
    "A1 600 700", 
    "A1 700 800", 
) 
(
    "A2 100 200", 
    "A2 200 300", 
    "A2 400 500", 
    "A2 500 600", 
    "A2 600 700", 
) 
+0

私はOPでも '$ col1> = $ p_col2'、おそらく' $ col1> = $ col2'をチェックしたいと思います。 – Qtax

+0

@ Qtax:彼は本当に欲しいとは思っていません。しかし、与えられた例によると、$ col1が$ p_col2 + 100より大きくない場合、行を保持したいと考えています。 「A1 200 300」と「A1 400 500」ではなく「A1 700 800」/「A1 1600 1700」 – Toto

+0

@ M42:ありがとうございます。私はあなたのコードとその作業を試しましたが、時には最後の行を与えていないこともあります。また、この出力が画面に表示され、ファイルに保存できません。出力をファイル(タブ区切り)に格納する方法はありますか?また、入力ファイルと同じ形式である必要があります。 (引用符なし、角括弧とカンマなし)。 – Vikas

関連する問題