You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用sed或awk将以数字开头的记录多行合并为单行?

需求与解决方案

问题描述

需要处理文本文件,仅将以数字开头的记录行及其后续所有关联行(直到下一个数字开头的记录出现)合并为单行,其余非记录行保持原样。

示例输入文本

max system cycles: 9087AED
max system scans: 900
Secure connection

date:....


1:    ID                 = XX_34_4_7_6e
      field1          = trc_1_1
      field2               = 24
      Blank field2          = 
      field3 XX       = OK (45)
      field4 XX               = assfsdf
      field5 XX YY      = sdffee (ssddT)
      field6 a b c d = no
      field7 ID            = zip
      field8               = city

2:    ID                 = YY_z3_4_t20
      field1          = xyz1_1_t
      field2               = 20
      Blank field2          = 
      field3 XX       = OK (5)

之前尝试的问题

  • 执行sed -e '/[0-9]/ N; s/\n/,/' /var/tmp/tmp1:仅能追加一行关联内容,且错误合并非记录行。
  • 执行sed '/./{H;$!d} ; x ; s/.\n/,/g; s/ *//g' /var/tmp/tmp1:会合并所有行,不符合仅处理数字记录的需求。

解决方案

方案1:使用Awk脚本(逻辑清晰易维护)

awk '
/^[0-9]+:/ {
    if (line != "") print line
    line = $0
    next
}
/^[[:space:]]+/ {
    sub(/^[[:space:]]+/, "", $0)
    line = line ", " $0
    next
}
{
    if (line != "") {
        print line
        line = ""
    }
    print $0
}
END {
    if (line != "") print line
}
' /var/tmp/tmp1

逻辑说明:

  • 匹配数字开头的记录行:若之前有缓存的合并行则先打印,再将当前行作为新合并行的起始。
  • 匹配空格开头的关联行:移除开头所有空格后,追加到当前合并行末尾(用, 分隔)。
  • 匹配其他非记录行:若有缓存的合并行先打印,再直接输出当前行,清空缓存。
  • 脚本结束时,若还有未打印的合并行则输出。

方案2:使用Sed脚本(纯文本流处理)

sed -n '
/^[0-9]/ {
    H
    :loop
    n
    /^[0-9]/! {
        s/^[[:space:]]*//
        H
        b loop
    }
    x
    s/\n/, /g
    p
    H
    b loop
}
/^[^0-9]/p
' /var/tmp/tmp1

逻辑说明:

  • 仅处理数字开头的行:先将该行存入保持空间。
  • 进入循环读取下一行:若不是数字开头,移除空格后存入保持空间,继续循环。
  • 遇到下一个数字开头的行:交换保持空间与模式空间,将所有换行替换为, 后打印,再将当前数字行存入保持空间,继续循环。
  • 非数字开头的行直接打印。

内容的提问来源于stack exchange,提问作者Rajeev

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.14 05:36:11