2011-09-27 69 views
93

我想编辑与sed的在OS X我使用下面的命令文件:就地编辑用的sed在OS X

sed 's/oldword/newword/' file.txt 

的输出被发送到终端。 file.txt未被修改。更改保存到FILE2.TXT用这个命令:

sed 's/oldword/newword/' file1.txt > file2.txt 

不过,我不希望另一个文件。我只想编辑file1.txt。我怎样才能做到这一点?

我试过了-i标志。这将导致以下错误:

sed: 1: "file1.txt": invalid command code f 
+2

什么,当你尝试'-i'标志您使用的确切命令? – eldarerathis

回答

191

您可以通过它提供一个后缀添加到备份文件正确使用-i标志。扩展您的示例:

sed -i.bu 's/oldword/newword/' file1.txt 

会给你两个文件:一个包含替代名称FILE1.TXT,以及一个包含有原始内容的名称file1.txt.bu。

轻度危险

如果你想破坏性覆盖原文件,使用这样的:

sed -i '' 's/oldword/newword/' file1.txt 
    ^note the space 

的因为线路被解析,是选项标志之间所需的空间的方式和它的参数,因为参数是零长度的。

除了可能摧毁你的原创,我不知道任何进一步的欺骗sed这种方式的危险。但是,需要注意的是,如果sed的这个调用是脚本的一部分,那么Unix Way™(恕我直言)将非破坏性地使用sed,测试它干净地退出,并且只删除无关的文件。

+0

你说得对,我在-i标志后省略了扩展名。除了可能弄乱原始文件(并且没有备份)之外,是否有其他原因是危险的? – SundayMonday

+0

根据'sed'手册页,如果设备上的磁盘空间不足,则可能会中途损坏文件并导致错误的输出结果。如果你正在使用本地源码控制'sed -i“”',在没有备份的情况下大多数情况下应该是正常的(或者只是运行sed之前的'git init && git add -A。&& git commit -m'backup'' '-i'模式)。 – cfeduke

+1

我发现温和的危险位特别有用。 +1 – Andre

12

我有类似的问题和MacOS

sed -i '' 's/oldword/newword/' file1.txt 

没有作品,但

sed -i"any_symbol" 's/oldword/newword/' file1.txt 

效果很好。

2

如已经建议的那样,您可以使用-i''--in-place)作为sed。请参阅:The -i in-place argument,但请注意,-i选项是非标准FreeBSD扩展,可能无法在其他操作系统上使用。其次sed is a Stream EDitor, not a file editor


替代的方法是使用内置的替代在Vim的Ex模式,如:

$ ex +%s/foo/bar/g -scwq file.txt 

和多文件:

$ ex +'bufdo!%s/foo/bar/g' -scxa *.* 

要递归编辑的所有文件,你如果shell支持该功能,则可以使用**/*.*(由shopt -s globstar启用)。


另一种方法是使用gawk及其新"inplace" extension如:

$ gawk -i inplace '{ gsub(/foo/, "bar") }; { print }' file1