1

我确实有需要在 awk、sed 和 shell 中解决的文本操作问题。
我的文字如下所示:

>Sample_1
    100                                                            101
    aaattattacaaaaataattacaaattattacaaaaagaattattacaaaaagaattacaaaa
-1.60   .(((((((.....)))))))...........................................  []
>Sample_2
    1                                35
    aattattacaaaaagaattattacaaaaagaatta
0.00    ...................................  _
>Sample_3
    1                                     123
    gctcacacctgtaatcccagcactttgggaggctgagg
-27.80  ((((.....))))......((((((.(((...))))))).)[][][[][]]
-26.40  (((((.((...(((((..((((((....)).........  [[][]][]
-25.80  ((((.....)))).....((((((...............  [][][][[][]]
    123                                  145
    ctgaggcaggcagatcacgaggtcacgagatcaa
-26.20  (((.....))))))  [][][[][]]
-25.90  ....((((..((....))  [][[][]]
-25.70  ..(((..((....))..(())  [[][]][[][]]
    145                                 256
    gtaatcccagcactttgggaggctgaggcaggcaga
0.00    ...........................................  _
    256                                 342
-25.00  ..((....((((.....((((((...)))....))...  [[][]]
-24.00  ..((.((((.((((())...  [[][][]]
-23.70  .((((((...(((((..((..  [[][]][]

我想要:

  1. 提取样品名称 ( >Sample_1);
  2. 提取样本名称之后的数值(它是 0 或负值);
  3. 从负值组(例如-27.80;-26.40;-25.80)中提取最先出现的数字(它是最负值)。

完美的输出如下所示:

>Sample_1  
-1.60  
>Sample_2  
0.00  
>Sample_3  
-27.80  
-26.20  
0.00  
-25.00

我尝试在 awk 打印 $1、grepping '>'、0 & 负值时执行此操作,但无法将列分成组 & 并提取最负值。

awk '{print $1}' file | egrep -i '>|0.00|-'
4

2 回答 2

3

sed你用and标记了你的问题awk,但如果你对 Perl 没问题,你可以写:

#!/usr/bin/perl -w

use warnings;
use strict;

my $min = undef;

while(<>)
{
  if(m/^(-?\d+\.\d+)/)
  {
    if(! defined($min) || $1 < $min)
      { $min = $1; }
  }
  else
  {
    if(defined $min)
    {
      print "$min\n";
      $min = undef;
    }
    if(m/^>/)
      { print; }
  }
}

if(defined $min)
  { print "$min\n"; }
于 2012-09-23T19:12:59.003 回答
1
awk '/^[0-]/ && new_group {print $1} {new_group = (/^[ \t]/)} /^>/' file
于 2012-09-23T19:52:32.583 回答