【问题标题】:Replace comma with newline in sed on MacOS?在 MacOS 上的 sed 中用换行符替换逗号?
【发布时间】:2012-05-31 16:25:18
【问题描述】:

我有一个逗号分隔的字符串文件。我正在尝试用新行替换逗号。我试过了:

sed 's/,/\n/g' file

但它不起作用。我错过了什么?

【问题讨论】:

  • 试试tr , '\n'。我猜,sed 将\n 视为纯文本。
  • 成功了!猫文件 | tr , '\n'
  • tr , '\n' < file - 没有管道。
  • 脚本末尾的g 是干什么用的?没有它我会得到相同的行为。
  • 你用的是什么外壳?这对我有用,使用 bash shell。

标签: macos unix sed


【解决方案1】:

改用tr

tr , '\n' < file

【讨论】:

  • 在 bash shell $ tr 中不工作,'\n' aitr 用法:tr [-Ccsu] string1 string2 tr [-Ccu] -d string1 tr [-Ccu] -s string1 tr [ -Ccu] -ds string1 string2
  • 用分号替换逗号也可以:tr ',' ';' &lt; input.csv &gt; output.csv
【解决方案2】:

使用ANSI-C quoted string $'string'

您需要一个反斜杠转义的文字换行符才能进入 sed。 至少在 bash 中,$'' 字符串将用真正的换行符替换 \n,但是您必须将 sed 看到的反斜杠加倍以转义换行符,例如

echo "a,b" | sed -e $'s/,/\\\n/g'

注意this will not work on all shells,但适用于最常见的。

【讨论】:

  • 奇怪,它还可以使用少一个反斜杠,即echo "a,b" | sed -e $'s/,/\\n/g
  • 赞成。有关详细信息,请参阅man bash 的“报价”部分。
  • 可以在 OSX 10.11 上使用:sed -E $'s/&lt;\\/br&gt;/\\\n/g' file,无需安装 gnu-sed
  • 通过给定的示例验证了在 OS X 10.7 上的工作。 -e 部分似乎没有必要。
  • 这太棒了!将此与 fzf 一起用于调试我的 $PATH 以防丢失:echo $PATH | sed -e $'s/:/\\\n/g' | fzf ^.^
【解决方案3】:
sed 's/,/\
/g'

适用于 Mac OS X。

【讨论】:

  • 谢谢你 - 想知道为什么我的旧 linux 技巧在 OSX 中不起作用。但确实如此!
  • 这是唯一适用于 sed 脚本的解决方案。
  • 请注意,反斜杠 转义 文字换行符(因此它不是命令终止符):它 不是 行继续符(如bash 等)。要查看差异,请尝试编写不带引号的上述命令:反斜杠将被 shell 解释为换行符,并且它和换行符将被丢弃。相反,将带引号的表达式(不带引号)的内容包含在单独的 comma-to-newline.sed 文件中(这消除了 shell 语法),它就可以工作了!
  • 这很好,因为它可以替换任何东西,而不是字符。 tr 似乎只适用于字符。如果您将字符串作为第一个参数,它将替换所有出现的字符,而不是字符串。
  • @Droogans 您使用的是 bash、sh 还是其他 shell?你确定你使用的是单引号而不是双引号?
【解决方案4】:

如果您的 sed 使用倾向于完全替换表达式(就像我的倾向于那样),您也可以改用 perl -pe

$ echo 'foo,bar,baz' | perl -pe 's/,/,\n/g'
foo,
bar,
baz

【讨论】:

    【解决方案5】:

    MacOS 不同,在 mac 中使用 sed 有两种方法可以解决这个问题

    • 首先,使用\'$'\n''替换\n,它可以在MacOS上运行:

      sed 's/,/\'$'\n''/g' file
      
    • 第二种,只用空行:

      sed 's/,/\
      /g' file
      
    • 附言。注意'分隔的范围

    • 第三种,用gnu​​-sed代替mac-sed

    【讨论】:

      【解决方案6】:

      显然\r 是关键!

      $ sed 's/, /\r/g' file3.txt > file4.txt
      

      改变了这个:

      ABFS, AIRM, AMED, BOSC, CALI, ECPG, FRGI, GERN, GTIV, HSON, IQNT, JRCC, LTRE,
      MACK, MIDD, NKTR, NPSP, PME, PTIX, REFR, RSOL, UBNT, UPI, YONG, ZEUS
      

      到这里:

      ABFS
      AIRM
      AMED
      BOSC
      CALI
      ECPG
      FRGI
      GERN
      GTIV
      HSON
      IQNT
      JRCC
      LTRE
      MACK
      MIDD
      NKTR
      NPSP
      PME
      PTIX
      REFR
      RSOL
      UBNT
      UPI
      YONG
      ZEUS
      

      【讨论】:

      • 我知道问题是 OS X,但这不适用于 GNU sed-4.2.2-6.fc20.x86_64。
      • 请记住,\r\n 不同,这可能会破坏进一步的数据操作和使用。
      • 抱歉,这对我不起作用。我只是在应该有换行符的地方得到一个 'r'。
      • 您应该在答案中更清楚地说明这给了\r
      • 它对我有用,但我想知道为什么! \n 是 unix 上的标准 stackoverflow.com/questions/1761051/difference-between-n-and-r
      【解决方案7】:

      这适用于 MacOS Mountain Lion (10.8)、Solaris 10 (SunOS 5.10) 和 RHE Linux(Red Hat Enterprise Linux Server 版本 5.3,Tikanga)...

      $ sed 's/{pattern}/\^J/g' foo.txt > foo2.txt
      

      ...^J 是通过 ctrl+v+j 完成的。请注意\^J 之前。

      PS,我知道 RHEL 中的 sed 是 GNU,MacOS sed 是基于 FreeBSD 的,虽然我不确定 Solaris sed,但我相信这几乎适用于任何 sed。 YMMV你...

      【讨论】:

        【解决方案8】:

        为了使它完整,这也有效:

        echo "a,b" | sed "s/,/\\$(echo -e '\n\r')/"
        

        【讨论】:

        • 这也适合混淆 C 竞赛,除了它是 Bash ;)
        • @AaronR。我同意 :-)。当然我更喜欢tr 解决方案,这已经是公认的答案。
        • 这适用于 OS X。为什么是 \n\r 而不是 \r\n?我尝试了\r\n,这是 Windows 上的必要命令。但是,在我这样做之后,它会在vim 中留下很多^M 回车字符,所以我认为它应该只是\n 但单独\n 不起作用。
        【解决方案9】:

        虽然我迟到了这篇文章,但只是更新我的发现。此答案仅适用于 Mac OS X。

        $ sed 's/new/
        > /g' m1.json > m2.json
        sed: 1: "s/new/
        /g": unescaped newline inside substitute pattern
        

        在上面的命令中,我尝试使用 Shift+Enter 添加新行,但不起作用。因此,这次我尝试按照错误提示“转义”“未转义的换行符”。

        $ sed 's/new/\
        > /g' m1.json > m2.json 
        

        成功了! (在 Mac OS X 10.9.3 中)

        【讨论】:

        • 这与你两年前 Max Nanasy 的回答没有什么不同。
        【解决方案10】:
        $ echo $PATH | sed -e $'s/:/\\\n/g' 
        /usr/local/sbin
        /Library/Oracle/instantclient_11_2/sdk
        /usr/local/bin
        

        ...

        在 Mojave 上为我工作

        【讨论】:

          【解决方案11】:

          只是为了澄清:OSX 上的 sed 手册页(10.8;达尔文内核版本 12.4.0)说:

          [...]

          Sed 正则表达式

           The regular expressions used in sed, by default, are basic regular expressions (BREs, see re_format(7) for more information), but extended
           (modern) regular expressions can be used instead if the -E flag is given.  In addition, sed has the following two additions to regular
           expressions:
          
           1.   In a context address, any character other than a backslash (``\'') or newline character may be used to delimit the regular expression.
                Also, putting a backslash character before the delimiting character causes the character to be treated literally.  For example, in the
                context address \xabc\xdefx, the RE delimiter is an ``x'' and the second ``x'' stands for itself, so that the regular expression is
                ``abcxdef''.
          
           2.   The escape sequence \n matches a newline character embedded in the pattern space.  You cannot, however, use a literal newline charac-
                ter in an address or in the substitute command.
          

          [...]

          所以我想必须使用 tr - 如上所述 - 或 nifty

          sed "s/,/^M
          /g"
          

          注意:您必须键入 ctrl>-v,return> 才能在 vi 编辑器中获取 '^M'

          【讨论】:

            【解决方案12】:

            macOS Mojave 上的 sed 于 2005 年发布,因此一种解决方案是安装 gnu-sed

            brew install gnu-sed
            

            然后使用gsed就可以了,

            gsed 's/,/\n/g' file
            

            如果您更喜欢sed,只需sudo sh -c 'echo /usr/local/opt/gnu-sed/libexec/gnubin &gt; /etc/paths.d/brew',这是brew info gnu-sed 建议的。重启你的任期,那么你在命令行中的sed就是gsed

            【讨论】:

              【解决方案13】:

              FWIW,以下行在 Windows 中有效,并用换行符替换我的路径变量中的分号。我正在使用安装在我的 git bin 目录下的工具。

              echo %path% | sed -e $'s/;/\\n/g' | less
              

              【讨论】:

                【解决方案14】:

                我发现另一个命令也可以工作。

                find your_filename.txt -type f -exec sed -i 's/,/\n/g' {} \;
                

                【讨论】:

                  猜你喜欢
                  • 2020-05-29
                  • 1970-01-01
                  • 1970-01-01
                  • 2022-10-23
                  • 2022-12-22
                  • 2022-12-22
                  • 1970-01-01
                  • 1970-01-01
                  • 2020-02-20
                  相关资源
                  最近更新 更多