使用sed / awk以节格式处理文件

时间:2013-05-03 05:52:39

标签: sed awk

我有一个stanza格式的文件。该文件的示例如下。

id_1:
        id=241
        pgrp=staff
        groups=staff
        home=/home/id_1
        shell=/usr/bin/ks
id_2:
        id=242
        pgrp=staff
        groups=staff
        home=/home/id_2
        shell=/usr/bin/ks

如何使用sed或awk处理它并仅在一行和制表符分隔格式中返回id名称,id和组? e.g:

id_1        241     staff
id_2        242     staff

6 个答案:

答案 0 :(得分:2)

用awk:

BEGIN { FS="="}

$1 ~ /id_/ { printf("%s", $1) }

$1 ~ /id/ && $1 !~ /_/ { printf("\t%s", $2) }

$1 ~ /groups/ { printf("\t%s\n", $2) }

答案 1 :(得分:0)

这是一个awk解决方案:

translate.awk

#!/usr/bin/awk -f
{
  if(match($1, /[^=]:[ ]*$/)){
    id_=$1
    sub(/:/,"",id_)
  }
  if(match($1,/id=/)){
    split($1,p,"=")
    id=p[2]
  }
  if(match($1,/groups=/)){
    split($1,p,"=")
    print id_," ",id," ",p[2]
  }
}

通过以下方式执行:

chmod +x translated.awk
./translated.awk data.txt

awk -f translated.awk data.txt

为了完整起见,这里有一个缩短的版本:

#!/usr/bin/awk -f
$1 ~ /[^=]:[ ]*$/ {sub(/:/,"",$1);printf $1" ";FS="="}
$1 ~ /id/         {printf $2" "}
$1 ~ /groups/     {print $2}

答案 2 :(得分:0)

 sed 'N;N;N;N;N;y/=\n/  /' data.txt | awk '{print $1,$3,$7}'

答案 3 :(得分:0)

通过设置RS

,这是单线方法
awk 'NR>1{print "id_"++i,$3,$7}' RS='id_[0-9]+:' FS='[=\n]' OFS='\t' file
id_1    241     staff
id_2    242     staff

需要GNU awk并假设ID从1开始递增。

如果ID的顺序是任意的:

awk '!/shell/&&NR>1{gsub(/:/,"",$1);print "id_"$1,$3,$5}' RS='id_' FS='[=\n]' OFS='\t' file
id_1    241     staff
id_2    242     staff

答案 4 :(得分:0)

awk -F"=" '/id_/{split($0,a,":");}/id=/{i=$2}/groups/{printf a[1]"\t"i"\t"$2"\n"}' your_file

测试如下:

> cat temp
id_1:
        id=241
        pgrp=staff
        groups=staff
        home=/home/id_1
        shell=/usr/bin/ks
id_2:
        id=242
        pgrp=staff
        groups=staff
        home=/home/id_2
        shell=/usr/bin/ks
> awk -F"=" '/id_/{split($0,a,":");}/id=/{i=$2}/groups/{printf a[1]"\t"i"\t"$2"\n"}' temp
id_1    241     staff
id_2    242     staff

答案 5 :(得分:0)

这可能适合你(GNU sed):

sed -rn '/^[^ :]+:/{N;N;N;s/:.*id=(\S+).*groups=(\S+).*/\t\1\t\2/p}' file

查找包含id的行,然后获取接下来的3行并重新排列输出。