我想使用awk组合从第4列开始直到列结尾的列。
输入:
1 682333 191.858 191517119 C A C A A A C A A A A A
2 1862626 71.9275 56032940 A C C C A A A C A C A A
3 11957134 155.78 150230950 B B B B A B A B A B A B
4 2516482 51.2692 31496569 B A A A A A A A A A A A
5 9378200 51.2798 31572927 A A B B B A A A A A B A
6 2071534 52.1573 32824318 A B A B A B A B B B A B
7 2074633 33.068 19035920 A A B A A A B A B A B A
8 7856856 121.811 117540910 A A A A A A A A B A B A
9 3741206 2.18574 2169864 A A A A A A A A A A A A
10 4411364 12.5959 24191374 C C A C A C C C A C A C
输出:
1 682333 191.858 191517119 CA CA AA CA AA AA
2 1862626 71.9275 56032940 AC CC AA AC AC AA
3 11957134 155.78 150230950 BB BB AB AB AB AB
4 2516482 51.2692 31496569 BA AA AA AA AA AA
5 9378200 51.2798 31572927 AA BB BA AA AA BA
6 2071534 52.1573 32824318 AB AB AB AB BB AB
7 2074633 33.068 19035920 AA BA AA BA BA BA
8 7856856 121.811 117540910 AA AA AA AA BA BA
9 3741206 2.18574 2169864 AA AA AA AA AA AA
10 4411364 12.5959 24191374 CC AC AC CC AC AC
顺便说一下,如果有一个awk命令教程的好网站,请在这里推荐。
答案 0 :(得分:3)
在我的书中,' one-liner'是一个滥用的术语,除非代码适合大约80个字符以下的单行。我认为当使用多行语句对多个语句进行格式化时,awk
代码更易于理解。因此,我想出了这个略有不同版本的代码。线路上有奇数个字段的情况并不需要特殊处理。访问$(NF+1)
将给出一个空字符串(或零号)。
awk '{ printf("%s\t%s\t%s\t%s", $1, $2, $3, $4)
for (i = 5; i <= NF; i += 2)
printf("\t%s%s", $i, $(i+1))
print ""
}' data
根据问题中的数据布局判断,在原始数据中使用了制表符分隔符,但是演示文稿的tabstops设置为4个空格。因此,代码使用制表符作为分隔符。我在包含以下内容的示例数据中添加了一行:
11 1111111 22.2222 33333333 D D W W X X Y Y Z Z =
我从中获得的输出加上问题中的数据在将tabstops设置为4格式化之后看起来像这样:
1 682333 191.858 191517119 CA CA AA CA AA AA
2 1862626 71.9275 56032940 AC CC AA AC AC AA
3 11957134 155.78 150230950 BB BB AB AB AB AB
4 2516482 51.2692 31496569 BA AA AA AA AA AA
5 9378200 51.2798 31572927 AA BB BA AA AA BA
6 2071534 52.1573 32824318 AB AB AB AB BB AB
7 2074633 33.068 19035920 AA BA AA BA BA BA
8 7856856 121.811 117540910 AA AA AA AA BA BA
9 3741206 2.18574 2169864 AA AA AA AA AA AA
10 4411364 12.5959 24191374 CC AC AC CC AC AC
11 1111111 22.2222 33333333 DD WW XX YY ZZ =
答案 1 :(得分:2)
与@sps答案非常相似,但没有if和using标签
awk '{ printf $1; for (i=2; i<=4; i++) {printf "\t%s",$i}; for (i=5; i<=NF; i+=2) { printf "\t%s%s",$i,$(i+1);} printf "\n"; }' filename
答案 2 :(得分:0)
这可能看起来很乱,但应该有效。
awk '{for(i=1; i<=4; i++) {printf "%s ",$i;} for(i=5; i<=NF; i++) {printf "%s", $i; if(i<NF){i++; printf "%s",$i;} printf "\t"} printf "\n"; }' filename
这里我们打印前4列 - 它们之间有两个空格(因此它们之间的任何原始格式都会改变) - 然后通过组合二对一打印剩余的列以及它们之间的标签(您可以将制表符更改为一些空格) )