如何使用sed替换换行符(\n)?

如何使用sed替换换行符(\n)?,sed,Sed,如何使用sed命令将换行符(\n)替换为空格() 我尝试过,但没有成功: sed 's#\n# #g' file sed 's#^$# #g' file 如何修复它?sed用于在线输入。尽管它可以满足你的需要 这里更好的选择是使用tr命令,如下所示: tr '\n' ' ' < input_filename tr'\n'

如何使用
sed
命令将换行符(
\n
)替换为空格(

我尝试过,但没有成功:

sed 's#\n# #g' file
sed 's#^$# #g' file

如何修复它?

sed
用于在线输入。尽管它可以满足你的需要


这里更好的选择是使用
tr
命令,如下所示:

tr '\n' ' ' < input_filename
tr'\n'
或完全删除换行符:

tr -d '\n' < input.txt > output.txt
tr-d'\n'output.txt
或者如果您有GNU版本(带有长选项)

tr--delete'\n'output.txt
该版本按照您预期的方式工作

perl -i -p -e 's/\n//' file

正如评论中所指出的,值得注意的是,这项修订已经到位
-i.bak
将在替换之前为您提供原始文件的备份,以防您的文件没有您想象的那么聪明。

我不是专家,但我猜在
sed
中,您首先需要使用“
N
”将下一行追加到模式空间中。摘自本书“高级sed命令”中的“多行模式空间”一节(Dale Dougherty和Arnold Robbins;O'Reilly 1997;第107页中):

multiline Next(N)命令通过读取新行输入并将其附加到模式空间的内容来创建多行模式空间。模式空间的原始内容和新的输入行用换行符分隔。嵌入的换行符可以通过转义序列“\n”在模式中匹配。在多行模式空间中,元字符“^”匹配模式空间的第一个字符,而不是任何嵌入换行符后的字符。类似地,“$”只匹配模式空间中的最终换行符,而不匹配任何嵌入的换行符。执行下一个命令后,控制权将传递给脚本中的后续命令

man sed

[2addr]N

将下一行输入追加到模式空间,使用嵌入的换行符将追加的内容与原始内容分开。请注意,当前行号会更改


我必须搜索(多个)格式不正确的日志文件,其中的搜索字符串可能位于下一行的“孤立”位置。

将此解决方案与GNU
sed一起使用

sed ':a;N;$!ba;s/\n/ /g' file
这将在循环中读取整个文件,然后用空格替换换行符

说明:

  • 通过
    :a
    创建标签
  • 通过
    N
    将当前行和下一行追加到模式空间
  • 如果我们在最后一行之前,请转到创建的标签
    $!ba
    $!
    表示不要在最后一行执行,因为应该有最后一行换行符)
  • 最后,替换用模式空间(即整个文件)上的一个空格替换每条换行符
  • 以下是适用于BSD和OS X的
    sed
    (根据)的跨平台兼容语法:


    如您所见,对这个简单的问题使用
    sed
    是有问题的。有关更简单和适当的解决方案,请参见。

    带有以下内容的答案:标签

    。。。在freebsd 7.2的命令行中不起作用:

    ( echo foo ; echo bar ) | sed ':a;N;$!ba;s/\n/ /g' sed: 1: ":a;N;$!ba;s/\n/ /g": unused label 'a;N;$!ba;s/\n/ /g' foo bar (echo foo;echo bar)| sed':a;N、 美元!文学士;s/\n//g' sed:1:“:a;N;$!ba;s/\N//g”:未使用的标签'a;N、 美元!文学士;s/\n//g' 福 酒吧 但是如果您将sed脚本放在文件中或使用-e“构建”sed脚本

    > (echo foo; echo bar) | sed -e :a -e N -e '$!ba' -e 's/\n/ /g' foo bar >(echo foo;echo bar)| sed-e:a-e N-e'$!ba'-e's/\n//g' 富吧 或者

    > cat > x.sed << eof
    :a
    N
    $!ba
    s/\n/ /g
    eof
    
    > (echo foo; echo bar) | sed -f x.sed
    foo bar
    
    >cat>x.sed(echo-foo;echo-bar)| sed-f x.sed
    富吧
    
    可能OS X中的sed与之类似。

    在Mac OS X上(使用FreeBSD sed):


    谁需要sed
    sed
    ?下面是
    bash
    方法:

    cat test.txt |  while read line; do echo -n "$line "; done
    
    针对上述“tr”解决方案,在Windows上(可能使用Gnuwin32版本的tr),建议的解决方案:

    tr '\n' ' ' < input
    
    tr'\n'
    不适用于我,它可能会出错,或者由于某种原因实际替换了\n w/“”

    使用tr的另一个功能,“删除”选项-d确实有效:

    tr -d '\n' < input
    
    tr-d'\n'
    或者用“\r\n”代替“\n”

    三件事

  • 绝对不需要
    tr
    (或
    cat
    等)。(GNU)
    sed
    和(GNU)
    awk
    相结合,可以完成99.9%的文本处理

  • 小溪!=基于行的
    ed
    是一个基于行的编辑器<代码>sed
    不可用。有关差异的更多信息,请参阅。大多数人把
    sed
    误认为是基于行的,因为默认情况下,它对简单匹配的模式匹配不是很贪婪-例如,当进行模式搜索并替换为一个或两个字符时,默认情况下它只替换找到的第一个匹配(除非全局命令另有规定)。如果全局命令是基于行而不是基于流的,则甚至不会有全局命令,因为它一次只计算行。尝试运行
    ed
    ;你会注意到区别<如果您想在特定行(例如for循环)上进行迭代,code>ed
    非常有用,但大多数时候您只需要
    sed

  • 尽管如此

    sed -e '{:q;N;s/\n/ /g;t q}' file
    
    在GNU
    sed
    4.2.1版中运行良好。上述命令将用空格替换所有换行符。它很难看,而且输入有点麻烦,但它工作得很好。
    {}
    可以省略,因为它们只是出于理智的原因才被包括在内

  • 要删除空行,请执行以下操作:

    sed -n "s/^$//;t;p;"
    
    使用Awk:

    awk "BEGIN { o=\"\" }  { o=o \" \" \$0 }  END { print o; }"
    

    我特别喜欢的一种解决方案是将所有文件追加到保留空间中,并替换文件末尾的所有换行符:

    $ (echo foo; echo bar) | sed -n 'H;${x;s/\n//g;p;}'
    foobar
    
    然而,有人告诉我,在某些sed实现中,保持空间可能是有限的。

    快速回答
    sed:a;N、 美元!文学士;s/\n//g'文件
    
  • :a创建标签“a”
  • N将下一行追加到图案空间
  • $如果不是
    sed -n "s/^$//;t;p;"
    
    awk "BEGIN { o=\"\" }  { o=o \" \" \$0 }  END { print o; }"
    
    $ (echo foo; echo bar) | sed -n 'H;${x;s/\n//g;p;}'
    foobar
    
    $ gawk 'BEGIN {RS="dn" } {gsub("\n"," ") ;print $0 }' file
    
    $ echo 'foo
    bar
    baz
    
    
    foo2
    bar2
    baz2' \
    | tr '\n' '\000' \
    | sed 's:\x00\x00.*:\n:g' \
    | tr '\000' '\n'
    
    foo
    bar
    baz
    
    echo -e "a\nb\nc\n" |tr '\n' '\t' | sed 's/\t/ <br> /g'`
    
    awk '{printf "%s ", $0}' inputfile
    
    awk '{printf "%s ", $0} END {printf "\n"}' inputfile
    
    awk '{printf "%s|", $0} END {printf "\n"}' inputfile
    
    awk 1 ORS=' '
    
    condition { code-block }
    
    printf '1\n2\n3\n' |
      sed 's/%/%p/g;s/@/%a/g' | tr '\n' @ | sed 's/@/<br>/g;s/%a/@/g;s/%p/%/g'
    
    1<br>2<br>3<br>
    
    tr '\n' ' ' 
    
    PROMPT~$ cat <<EOF |sed 's/$/===/g'
    first line
    second line
    3rd line
    EOF
    
    first line===
    second line===
    3rd line===
    PROMPT~$
    
    PROMPT~$ cat <<EOF | tr '\n' $'\x01'|sed -e 's/\x01/===/g'
    first line
    second line
    3rd line
    EOF
    
    first line===second line===3rd line===PROMPT~$
    
    od -A n -t o1 -v | tr ' \t' '\n\n' | grep . |
      while read x; do [ "0$x" -eq 012 ] && printf '<br>\n' || printf "\\$x"; done
    
    seq 10 | xargs
    
    seq 10 | xargs echo -n
    
    sed 'x;G;1!h;s/\n/ /g;$!d'
    
    x   - which is used to exchange the data from both space (pattern and hold).
    G   - which is used to append the data from hold space to pattern space.
    h   - which is used to copy the pattern space to hold space.
    1!h - During first line won't copy pattern space to hold space due to \n is
          available in pattern space.
    $!d - Clear the pattern space every time before getting the next line until the
          the last line.
    
    sed -z 's/\n/ /g'
    
    sed ':a;N;$!ba;y/\n/ /'
    
    sed -e ':a' -e 'N;$!ba' -e 'y/\n/ /'
    
    sed -ie -z 's/Marker\n/# Marker Comment\nMarker\n/g' myfile.txt
    
    tr '\r\n' ' ' < $input > $output
    
    awk '{printf $0}' file
    
    awk '{printf $0 " "}' file