【问题标题】:How to sequence lines in files if some lines are strings如果某些行是字符串,如何对文件中的行进行排序
【发布时间】:2016-03-30 19:24:40
【问题描述】:

我遇到了 bash 的问题,我最近开始使用它。 我意识到很多神奇的东西可以只用一行来完成,因为我之前的问题已经被它解决了。 这次的问题很简单:

我有一个具有这种格式的文件

2 2 10
custom
8 10
3 5 18
custom
1 5

某些行等于字符串custom(可以是任何行!),其他行包含2或3个数字。 我想要一个文件,它将用数字对行进行排序,但保持自定义的行(顺序也必须相同),所以所需的输出是

2 4 6 8 10
custom
8 9 10
3 8 13 18
custom
1 2 3 4 5

我也希望用这个覆盖输入文件。 我知道使用 seq 我可以进行排序,但我希望以优雅的方式在文件中进行。

【问题讨论】:

    标签: bash awk sed seq


    【解决方案1】:

    你可以像这样使用 awk:

    awk '/^([[:blank:]]*[[:digit:]]+){2,3}[[:blank:]]*$/ {
       j = (NF==3) ? $2 : 1
       s=""
       for(i=$1; i<=$NF; i+=j)
          s = sprintf("%s%s%s", s, (i==$1)?"":OFS, i)
       $0=s
    } 1' file
    
    2 4 6 8 10
    custom
    8 9 10
    3 8 13 18
    custom
    1 2 3 4 5
    

    说明:

    • /^([[:blank:]]*[[:digit:]]+){2,3}[[:blank:]]*$/ - 仅匹配包含 2 或 3 个数字的行。
    • j = (NF==3) ? $2 : 1 - 如果有 3 列,则将变量 j 设置为 $2,否则将 j 设置为 1
    • for(i=$1; i&lt;=$NF; i+=j) 从第一个 col 到最后一个 col 循环,增加 j
    • sprintf 用于格式化生成的序列
    • 1 是打印每一行的默认 awk 操作

    【讨论】:

    • custom 可以是任意行,也可以是1 strange line。从问题中不清楚,赞成直接的解决方案。
    • 它没有用。也许我应该更清楚一点,任何行都可以等于 custom 并且它实际上是字符串“custom”,其他行可以有 2 或 3 个数字,它可以是行中的任何数字,我测试这个代码文件这是 2 2 10;风俗; 2 6 10;风俗; 1 5 (; 代表行),注意 2 6 10 的输出应该是 2 6 - 我真的想在任何不等于 custom 的行上执行 seq 命令
    • 如果有帮助,文件可以有 1、2 或 3 行。我没有提到这一点,因为我想要更通用的解决方案。由于文件中的最大行数为 3,我可以通过很多 if else 语句手动解决这个问题,它可以处理所有 8 种情况,但我希望有更优雅的解决方案。
    • 和 seq 一样,2 3 4 5 6(如果未指定 step,它将等于 1)
    • 我很抱歉,它现在可以工作了。但是,当我将其作为复制粘贴代码输入时,它只会打印 file1 的内容,当我像在您的演示中那样输入一行时,它可以完美运行。你对此有解释吗?我对 bash 很陌生。
    【解决方案2】:

    这可能对你有用(GNU sed、seq 和 paste):

    sed '/^[0-9]/s/.*/seq & | paste -sd\\  /e' file
    

    如果一行以数字开头,则使用该行的值作为 seq 命令的参数,然后将其通过管道传输到 paste 命令。替换命令的 RHS 使用 e 标志(GNU sed 特定)进行评估。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-07-02
      • 2018-10-10
      • 1970-01-01
      • 2014-05-23
      • 1970-01-01
      • 2011-01-23
      • 1970-01-01
      • 2016-10-11
      相关资源
      最近更新 更多