pipe sed命令用来创建多个文件

时间:2014-07-09 20:37:26

标签: regex shell command-line sed

我需要在多次出现的文件中将X转换为Y,每次匹配将保存到文件的出现次数。

这是一个示例文件(demo.txt):

\x00START how are you? END\x00
\x00START good thanks END\x00
sometimes random things\x00\x00 inbetween it (ignore this text)
\x00START thats nice END\x00

现在运行命令后,除了&#之外,每个文件(/folder/demo1.txt,/folder/demo2.txt等)的内容应该是\ x00START和END \ x00之间的内容(\ x00为空) 39; START'但不是'结束'

/folder/demo1.txt应该说" START你好吗? ",/ folder / demo2.txt应该说" START非常感谢"。

所以基本上它应该管道#34;你好吗?"并使用' echo'我可以在前面加上' START'。

值得记住的是,我正在处理一个非常大的二进制文件。

我目前正在使用

sed -n -e '/\x00START/,/END\x00/ p' demo.txt > demo1.txt

但是这没有达到预期的效果(它在' \ x00START'之前排队,并且不会在第一个' END \ x00&#停止#' 39。)

3 个答案:

答案 0 :(得分:1)

您可以使用grep

grep -Po "START\s+\K.*?(?=END)" file
how are you? 
good thanks 
thats nice 

说明:

  1. -P允许Perl正则表达式
  2. -o仅提取匹配的模式
  3. -K积极向后看
  4. (?=something)积极向前看
  5. 编辑:要将\00START匹配,END可能会出现在:

    之间
    echo -e '\00START hi how are you END\00' | grep -aPo '\00START\K.*?(?=END\00)'
     hi how are you
    

    EDIT2:使用grep的解决方案只匹配单行,对于多行,最好使用perl。语法非常相似:

    echo -e '\00START hi \n how\n are\n you END\00' | perl -ne 'BEGIN{undef $/ } /\A.*?\00START\K((.|\n)*?)(?=END)/gm; print $1' 
     hi 
     how
     are
     you 
    

    这里有什么新鲜事:

    1. undef $/取消定义INPUT分隔符$/,默认为'\ n'
    2. (.|\n)*点几乎匹配任何字符,但不匹配 \n所以我们需要在此处添加。
    3. /gm修改器,g用于多行的全局m

答案 1 :(得分:1)

如果你有 GNU awk,请尝试:

 awk -v RS='\0START|END\0' '
      length($0) {printf "START%s\n", $0 > ("folder/demo"++i".txt")}
      ' demo.txt
  • RS='\0START|END\0'定义一个充当 [input] Record Separator 的正则表达式,它将输入文件按\0START和{{1}之间的字符串(字节序列)分成记录(END\0代表\0(null char。)here。
    • 使用多字符,基于正则表达式的记录单独符合POSIX标准; GNU NUL支持它(一般情况下awk ,但似乎没有mawk字符。)。
  • 模式NUL可确保仅在记录非空
  • 时才执行相关操作(length($0))。
  • {...}{printf "START%s\n", $0 > ("folder/demo"++i)}前面的每个非空记录输出到文件"START",其中folder/demo{n}.txt"表示以{n}开头的序列号。

答案 2 :(得分:0)

我会将空值转换为换行符,以便grep可以在一条干净的行上找到您想要的文本:

tr '\000' '\n' < yourfile.bin | grep "^START"

从那里你可以像以前一样把它带进sed