通过替换一些分隔符并过滤其中的数据来处理文件

时间:2015-09-01 19:03:54

标签: regex perl shell awk sed

我正在尝试处理一个巨大的文件,如果数据需要修改结构。我的文件有117列但是为了简单起见,让我们假设我有一个包含10列的文件 示例文件:

public class BaseClass
 {
    public bool SupportsA
    {
        get { return (this.GetType().GetMethod("A").DeclaringType == typeof(BaseClass)); }
    }
    public virtual void A()
    {
        // Null default implementation.
    }
}

我现在想要 - 包括col6到col10的列名和列值 - 并用' |'替换分隔符。从col6到col10为整个文件

必需的输出

android:layout_height="wrap_content"

这是可能的吗?我对regex / awk完全陌生。有人可以帮忙吗

P.S:处理完数据后,我试图从' |'中清除零。分隔栏......

col1, col2, col3, col4, col5, col6, col7, col8, col9, col10
1,2,3,4,5,6,7,8,9,10

2 个答案:

答案 0 :(得分:5)

你可以使用这个awk:

awk -F ', *' 'NR==1{for (i=1; i<=NF; i++) hdr[i]=$i; next}
  {for (i=1; i<=NF; i++) printf "%s%s", ((i>5)?hdr[i] ":":"") $i,
      ((i<NF)? ((i>5)?"|":",") : ORS)}' file

<强>输出:

1,2,3,4,5,col6:6|col7:7|col8:8|col9:9|col10:10

hdr是在NR==1

时保存标题列名称的关联数组

更新:根据评论,OP希望跳过零值的列。您可以使用:根据评论,OP希望跳过零值的列。您可以使用:

awk -F ', *' 'NR==1{for (i=1; i<=NF; i++) hdr[i]=$i; next}
   {for (i=1; i<=NF; i++) if ($i>0) printf "%s%s", ((i>5)?hdr[i] ":":"") $i,
            ((i<NF)? ((i>5)?"|":",") : ORS)}' file

答案 1 :(得分:0)

sed '1 {h
        s/\([^,]*,\)\{5\}\(\([^,]*,\)\{4\}[^,]*\).*/\2/
        s/,/|/g
        x
        b
       }
   G
   s/\(\([^,]*,\)\{5\}\)\([^,]*,\)\{4\}[^,]*\(.*\)\n\(.*\)/\1\5\4/
   ' YourFile

Posix sed版本:

  • 假设字段值中没有,
  • 调整指数
    • 5到现场开始 - 1(本样本中为6)
    • 4要捕获的字段数[最后一个索引 - 起始索引](此示例中10 - 6 = 4)
    • 如果字段捕获从1开始需要修改(\{0\}可能会出现意外行为,具体取决于sed版本)

原理:

  • 从第1行获取子字段,更改分隔符并将其放入保留缓冲区,然后打印原始标题
  • 对于所有其他行,将新增值添加到该行,在新行后添加子字段信息(因此添加值),打印结果