2013-01-16 64 views
0

我读了这个问题 Awk code to select multiple patterns需要了解这个AWK声明

的用户在此输入

------------------------------------------------------------------------ 
r4544 | n479826 | 2012-08-28 07:12:33 -0400 (Tue, 28 Aug 2012) | 1 line 
Changed paths: 
    M /branches/8.6.0/conf/src/main/config/RTSConfig.xml 

CET-402: some text comment 
------------------------------------------------------------------------ 
r4550 | n479826 | 2012-09-04 05:51:29 -0400 (Tue, 04 Sep 2012) | 1 line 
Changed paths: 
    M /branches/8.6.0/conf/src/main/config/RTSConfig.xml 
    M /branches/8.6.0/conf/src/main/config/base.cfg 
    M /branches/8.6.0/conf/src/main/config/prod.cfg 
    M /branches/8.6.0/conf/src/main/config/qa.cfg 
    M /branches/8.6.0/conf/src/main/config/uat.cfg 

CET-438: some text comment 

,他希望以此为输出

r4544 | n479826 | 2012-08-28 07:12:33 | /branches/8.6.0/conf/src/main/config/RTSConfig.xml 
r4550 | n479826 | 2012-09-04 05:51:29 | /branches/8.6.0/conf/src/main/config/RTSConfig.xml 
r4550 | n479826 | 2012-09-04 05:51:29 | /branches/8.6.0/conf/src/main/config/base.cfg 
r4550 | n479826 | 2012-09-04 05:51:29 | /branches/8.6.0/conf/src/main/config/prod.cfg 
r4550 | n479826 | 2012-09-04 05:51:29 | /branches/8.6.0/conf/src/main/config/qa.cfg 
r4550 | n479826 | 2012-09-04 05:51:29 | /branches/8.6.0/conf/src/main/config/uat.cfg 

正确答案是此

awk -F"|" '/^r/{a=$1;b=$2;c=substr($3,0,20)}/^ M/{gsub(/ M /," ");print a"|"b"|"c"|"$0}' your_file 

我没有完全理解。

现在,我得到这部分

/^r/{a=$1;b=$2;c=substr($3,0,20)}/^

,但我没有得到第二部分 M/{gsub(/ M /," ");print a"|"b"|"c"|"$0}

我的问题是

  1. 什么是开始 M手段2.现在awk会逐行读取文件,所以它表示在第二行 即Chngaed路径a =0的价值,因为没有字段分隔符|在该行
  2. 现在当AWK涉及到第三行 然后再a,b,c =0$0 = /bracnhes但如何结果仍然显示的旧值,B, ç

AWK时使用多线

回答

1

我很懒得解释了答案:) 但还是让我把我的lazyness搁置一段时间了:

/^r/{a=$1;b=$2;c=substr($3,0,20)} 

以上代码块仅在行以字母r开头时才会执行。 块里面说的,第二场第一场从输入存储在B和第三个字段是:

2012-08-28 07:12:33 -0400 (Tue, 28 Aug 2012) 

,但我只需要日期与时间戳,其余的都是过时的我。 它总是20个字符。 所以我从第三个字段取出一个子字符串并将其存储在c中。

我的主要兴趣是以/^M /开头的行,我必须显示上一行中以r 开头的信息,并确保在我们所需的行之前有一行以r开始的行其中有所有的信息我必须预先添加以M开头的行。

所以每当一行以M开始时,都会预先存储在ab和c中的值。

M/{gsub(/ M /," ");print a"|"b"|"c"|"$0} 

gsub部分将从当前行删除“M”部分的空格。 打印部分只是将b和c的值预先添加到当前行的|作为分隔符。

这就是逻辑!

我将回到我的懒人模式现在:)

1

做这样的

/^r/{a=$1;b=$2;c=substr($3,0,20)}

我越来越糊涂
  1. 它匹配从r和一些数字开始的唯一行。因此它的A,B,C变量

/^ M/{gsub(/ M /," ");print a"|"b"|"c"|"$0}

  1. 这与spaces and M行strating得到其他部分相匹配。在此匹配,在A,B,C将fteched形成以前保存的值
0

的原因是一个,b和c的值遇到M个之前不会被替换。所以它仍然附加到打印语句中。