为什么不“csplit”和“grep”同意是否有匹配?

时间:2017-09-25 21:02:58

标签: regex bash macos grep csplit

我正在尝试在BASH中使用csplit将文件在1500-1600中分隔为年份作为分隔符。

当我执行命令时

csplit Shakespeare.txt '/1[56]../' '{36}'

除了至少两个问题外,它几乎可以运作:

  1. 这会输出38个文件,而不是36个,编号为xx00xx37。 (xx00也完全空白。)我不明白这是怎么回事。
  2. 其中一个文件(为什么csplit会返回37个非空文件而不是我预期的36个非空文件?不会开头15XX或16XX - 以" ACT 4 SCENE 15 \ n"开头(其中\ n应该表示换行符或换行符)。我不明白csplit如何使用数字匹配新的广告/换行符。
  3. 当我执行命令时(这是我想要的)

    csplit Shakespeare.txt '/1[56][0-9][0-9]/' '{36}'

    终端返回错误:csplit: 1[56][0-9][0-9]: no match,并列出执行上述操作时列出的所有数字。

    这对我来说特别有意义,因为grep另有说法:

    grep -c "1[56][0-9][0-9]" Shakespeare.txt
    36

    grep -c "1[56].." Shakespeare.txt
    36

    注意: man csplit表示我从2005年1月26日开始拥有BSD版本。man grep表示我拥有自2010年7月28日起的BSD版本。

1 个答案:

答案 0 :(得分:0)

根据here by user 'DRL' on 06-20-2008给出的答案,我决定尝试将-k选项添加到csplit

csplit -k Shakespeare.txt '/^1[56][0-9][0-9]/' '{36}'

这会返回错误:csplit: ^1[56][0-9][0-9]: no match

但是,它仍然提供(或多或少)所需的输出:文件xx00.txtxx36.txt xx37.txt),每个非-empty文件xx01.txt - xx36.txt包含预期/期望的内容。 (特别是,没有文件以" ACT 4 SCENE 15"

开头

csplit的手册页说明了-k标志的以下内容:

  

-k如果发生错误或收到HUP,INT或TERM信号,请不要删除输出文件。

老实说,我不太明白这意味着什么,但我仍然有以下猜想,为什么这个解决方案有效/可行:

猜想: csplit期望文件的开头与正则表达式匹配。因此,由于文件的起始行与^1[56][0-9][0-9]不匹配,因此它会发出颤抖并退出而没有-k标志。

然而,我仍然不明白为什么1[56][0-9][0-9]不起作用,也许是同样的原因。而且我绝对不明白为什么1[56]..不起作用(即为什么csplit生成了第37个不以模式开头的文件)。