【问题标题】:read from nth occurence of string till a specific string从第 n 次出现的字符串读取直到特定的字符串
【发布时间】:2013-11-03 04:02:15
【问题描述】:

我有一个包含内容的文件:

[属性]
名称=“名称1”
默认=“abcd”
[表格]
名称="tabCol"
默认=“abcd”
类型="abc"
[表格]
名称="tabCol1"
默认=“abcd1”
类型="abc1"
[表格]
名称="tabCol2"
默认=“abcd2”
type="abc2"

我想获取具体的标题内容。就像我想要标题 [ATTRIBUTES] 第一次出现的内容一样,输出应该是:

[属性]
名称=“名称1”
默认=“abcd”

同样如果想要标题表第二次出现的内容,输出应该是:

[表格]
名称="tabCol1"
默认=“abcd1”
类型="abc1"

这我必须使用 unix shell 脚本来做。我想最好使用 sed,但不知道如何。
所以请帮忙。
提前致谢

【问题讨论】:

    标签: unix sed


    【解决方案1】:

    这是另一种使用 awk 的方法:

    parse.awk

    BEGIN { FS = "[][]" }
    /^\[/ && f  == n       { exit }
    /^\[/ && $2 == heading { f++  }
    f == n
    

    像这样运行它:

    awk -f parse.awk heading=TABLE n=2 infile
    

    输出:

    [TABLE]
    name="tabCol1"
    default="abcd1"
    type="abc1"
    

    【讨论】:

      【解决方案2】:

      使用 和适当的 ini 文件解析器:

      $ perl -MConfig::IniFiles -e '
          my $cfg = new Config::IniFiles -file => "./conf";
          printf "[ATTRIBUTES]\nname=%s\ndefault=%s\n",
              $cfg->val("ATTRIBUTES", "name"),
              $cfg->val("ATTRIBUTES", "default");
      ' conf
      [ATTRIBUTES]
      name="name1"
      default="abcd"
      

      【讨论】:

        【解决方案3】:

        这可能对你有用(GNU sed):

        sed -r '/^\[ATTRIBUTES]/!d;x;s/^/X/;/^X{1}$/{x;:a;$q;n;/^\[/Q;ba};x;d' file
        

        对于第一个 ATTRIBUTES 块,或者:

        sed -r '/^\[TABLE]/!d;x;s/^/X/;/^X{1}$/{x;:a;$q;n;/^\[/Q;ba};x;d' file
        

        对于第一个 TABLE 块,或者:

        sed -r '/^\[TABLE]/!d;x;s/^/X/;/^X{2}$/{x;:a;$q;n;/^\[/Q;ba};x;d' file
        

        对于第二个TABLE 块或:

        sed -r '/^\[TABLE]/!d;x;s/^/X/;/^X{3}$/{x;:a;$q;n;/^\[/Q;ba};x;d' file
        

        第三个TABLE 块。

        【讨论】:

          【解决方案4】:

          仅打印第二次出现的 TABLE 部分:

          恐怕在 sed 中不可能。另一方面,awk...

          awk 'BEGIN { x = 0 } ; /^\[TABLE\]/ { x = x + 1 } ; (x == 2) { print }' foo.txt
          

          当然,除非您的文件内容如此(即所有 TABLE 部分都在文件末尾一次运行),否则这会失败。要以单行方式正确实现这一点,需要 perl:

          perl -ne '$count{$tag = $1} += 1 if /^\[(.*?)\]$/; print if ($tag == "TABLE" && $count{$tag} == 2)' < foo.txt
          

          【讨论】:

            【解决方案5】:

            有些人喜欢这样使用awk

            awk 'BEGIN {printf "["} NR%2==0' RS="[" ORS="[" file
            ATTRIBUTES]
            name="name1"
            default="abcd"
            [TABLE]
            name="tabCol1"
            default="abcd1"
            type="abc1"
            

            【讨论】:

              【解决方案6】:
              MyBloc="TABLE"
              MyOccurence=2
              
              sed -n "H
              $ {s/$/\
              \[/;^s/\(.*\[${MyBloc}\]\){${MyOccurence}\}\(.*\n\)\[\(.*\)$/\[${MyBloc}\]\2/p" YourFile
              

              (现在这里没有要测试的会话)

              【讨论】:

                猜你喜欢
                • 2012-09-04
                • 2016-07-25
                • 2012-01-05
                • 2011-10-29
                • 2022-01-18
                • 1970-01-01
                • 2010-12-25
                • 2016-05-07
                相关资源
                最近更新 更多