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

如何使用sed匹配并替换连续两行内容?

解决连续数字开头行的交换与去数字问题

我明白你遇到的痛点了——直接用N命令会把非数字开头的行也卷进来,导致匹配逻辑混乱,没法精准定位连续两行都是数字开头的情况。下面我给你两种可靠的解决方案,分别用sed和awk实现,完全符合你的需求:

方案1:用sed精准匹配处理

sed的核心思路是只对数字开头的行触发后续逻辑,避免误读非目标行。命令如下:

sed -E ':loop; /^[0-9]/ {N; /\n[0-9]/ {s/^[0-9](.*)\n[0-9](.*)/\2\n\1/; b loop}; P; D}' 你的文件名.txt

逐部分解释:

  • -E:启用扩展正则,不用转义括号,写法更简洁
  • :loop:定义循环标签,处理完一组连续行后可以回头检查新的行组合
  • /^[0-9]/ { ... }:只有当前行以数字开头时,才执行大括号内的操作
    • N:读取下一行到模式空间,此时模式空间是行1\n行2
    • /\n[0-9]/ { ... }:检查第二行是否也以数字开头,是的话执行替换
      • s/^[0-9](.*)\n[0-9](.*)/\2\n\1/:捕获两行数字后的内容,交换位置并去掉开头数字
      • b loop:回到循环标签,确保如果交换后仍有连续数字行,能继续处理
    • P; D:如果第二行不是数字开头,就打印模式空间的第一行,删掉它后重新处理剩余内容,不破坏原有行结构

方案2:用awk实现更直观的逻辑

awk的变量特性让我们可以轻松保存上一行内容,逻辑更易懂:

awk '
prev ~ /^[0-9]/ && /^[0-9]/ {
    sub(/^[0-9]/, "", prev)
    sub(/^[0-9]/, "", $0)
    print $0
    print prev
    prev = ""
    next
}
prev != "" {
    sub(/^[0-9]/, "", prev)
    print prev
}
{ prev = $0 }
END {
    if (prev != "") {
        sub(/^[0-9]/, "", prev)
        print prev
    }
}' 你的文件名.txt

逻辑说明:

  1. 用prev变量缓存上一行内容
  2. 当当前行和上一行都以数字开头时,去掉两行的开头数字,先打印当前行再打印上一行(完成交换),然后清空prev
  3. 如果prev不为空,说明上一行无法和当前行组成连续数字行,打印去数字后的prev
  4. 最后缓存当前行到prev,END块处理最后一行剩余内容

测试示例

拿你提供的示例文件2来说,假设原内容是:

adfa adaf dfd
aaa
1 1a
2 2b
3 3d
sdfa
4 4a
5 5b
6 6d
7 7k

执行命令后,输出会变成:

adfa adaf dfd
aaa
2b
1a
3d
sdfa
4a
5b
6d
7k

完全符合“交换连续数字行+去开头数字”的要求。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.27 03:22:59