【问题标题】:Modifying text using awk使用 awk 修改文本
【发布时间】:2012-11-23 12:02:08
【问题描述】:

我正在尝试使用 awk 修改文本文件。一共有三列,我想删除第一列的部分文字:

range=chr1      20802865        20802871        
range=chr1      23866528        23866534

chr1      20802865        20802871        
chr1      23866528        23866534

我该怎么做?

我试过awk '{ substr("range=chr*", 7) }'awk '{sub(/[^[:space:]]*\\/, "")}1' 但它会删除文件的所有内容。

【问题讨论】:

  • 下面的答案描述了更好的方法,但要明确一点:你当前的awk 命令的问题是你从不打印任何东西。在awk 中,如果指定地址不带命令,则默认命令打印整行;但是由于您正在指定命令(通过使用{ ... }),除非您明确告诉它(通过调用print),否则它实际上不会打印任何内容。

标签: linux text replace sed awk


【解决方案1】:

设置字段分隔符为=并打印第二个字段:

# With awk                                                                     
$ awk -F= '{print $2}' file
chr1      20802865        20802871        
chr1      23866528        23866534

# Or with cut
$ cut -d= -f2 file                  
chr1      20802865        20802871        
chr1      23866528        23866534

# How about grep
$ grep -Po '(?<==).*' file
chr1      20802865        20802871        
chr1      23866528        23866534

# Temp file needed
$ cut -d= -f2 file > tmp; mv tmp file

如果要将更改存储回fileawkcutgrep 都需要临时文件,更好的解决方案是使用sed

 sed -i 's/range=//' file

这将替换 range= 没有任何内容,-i 表示更改已就地完成,因此无需像 sed 那样处理临时文件。

【讨论】:

    【解决方案2】:

    如果你不需要使用awk,你可以使用sed,我觉得更简单一些。希望您熟悉正则表达式运算符,例如 ^.

    $ cat awkens
    range=chr1      20802865        20802871
    range=chr1      23866528        23866534
    $ sed 's/^range=//' awkens
    chr1      20802865        20802871
    chr1      23866528        23866534
    

    【讨论】:

      【解决方案3】:

      看起来您在文件中使用制表符而不是空格作为分隔符,所以:

      awk 'BEGIN{FS="[=\t]"; OFS="\t"} {print $2, $3, $4}' input_file
      

      awk 'BEGIN{FS="[=\t]"; OFS="\t"} {$1=""; gsub("\t\t", "\t"); print}' input_file
      

      【讨论】:

      • 在 awk 中删除字段很尴尬。删除字段 1 的另一种方法:for (i=2; i&lt;=NF; i++) $(i-1)=$i; NF--
      猜你喜欢
      • 2011-01-10
      • 1970-01-01
      • 1970-01-01
      • 2013-02-18
      • 2015-03-19
      • 2021-02-23
      • 2013-01-26
      • 2021-04-23
      相关资源
      最近更新 更多