繁体   English   中英

使用awk检查一行中的多个位置以获取数据

[英]Examine multiple locations in a line for data using awk

我试图提取一些最初来自大型机的信息。 这些行全都是ASCII字符数据,但是每一行都被认为是多段的,因此具有不同的行长。 字段由长度定界。 该行中有一个字段,指示该行中可变部分应有多少段。 我要做的是在这些可变段中寻找指标的存在,并从中提取一些数据。

简化示例如下所示;

UUID12345 1   ABC 1 345  
UUID23456 2   XYZ 4 763 ABC 4 678  
UUID34567 3   XYZ 4 763 ABC 2 456 QRS 2 456  
UUID45678 2   DEF 1 345 TUV 8 111 
UUID56789 0

第二列规定了期望的细分数。 可以有多达99个段,但在现实中,有小于10。在上面的例子中,每个段将包含起始于ABC对例如第一行中的位置的10个字节。 我要提取的是每行的第一列,以及包含ABC的任何段的后3个字符的值。

因此,上面一行的示例输出为:

UUID12345 345  
UUID23456 678  
UUID34567 456
UUID45678 
UUID56789 

我知道一些非常基本的awk,可以查找一行的特定部分,但是不知道如何实现此目的。 例如,以下内容使我能够提取第一行,但只能通过查看特定位置来进行提取,而无需考虑指示可变段数的第二列。

awk '{ if (substr($0, 0, 4)=="UUID" && substr($0, 15, 3)=="ABC") {print substr($0, 0, 9) " " substr ($0, 21,3)}}' <<< "UUID12345 1   ABC 1 345"

编辑

根据我在下面对Ed Morton的评论,这就是我最终对我有用的东西(其中test.txt是上面显示的示例);

awk '{segs=substr($0, 11, 1); acc=substr($0, 1, 10); startCol=15; val=""; for(i=startCol; i<startCol+(10 * segs); i+= 10) if (substr($0, i, 3)=="ABC") val=substr($0, i + 6, 3); print acc " " segs " " val}' test.txt
$ awk '{val=""; for (i=3; i<NF; i+=3) if ($i=="ABC") val=$(i+2); print $1, val}' file
UUID12345 345
UUID23456 678
UUID34567 456
UUID45678
UUID56789

如果还不够,那么请编辑您的问题,以提供更真实的代表性示例输入/输出,更好地满足您的所有需求。

用awk的另一种方式:

awk -F'ABC' '{split($1,a," |\t");split($2,b," |\t");print a[1],b[3]}' infile

使用Perl

$ perl -lane ' ($x)=$_=~/\bABC\s+\S+\s+(\S+)/; print $F[0], " ", $x ' moose.txt
UUID12345 345
UUID23456 678
UUID34567 456
UUID45678
UUID56789

$ cat moose.txt
UUID12345 1   ABC 1 345
UUID23456 2   XYZ 4 763 ABC 4 678
UUID34567 3   XYZ 4 763 ABC 2 456 QRS 2 456
UUID45678 2   DEF 1 345 TUV 8 111
UUID56789 0

$

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM