我想用另一组中的相应字符替换一组字符,如下所示:
original set: ots
"target" set: u.x
foobartest → fuubar.ex.
像这样的翻译/音译是该命令的特色tr
:
$ echo 'foobartest' | tr 'ots' 'u.x'
fuubar.ex.
不幸的是,tr
不支持像那样就地更改文件sed
。
我想使用sed
这样我就不必重新发明临时文件的轮子。
答案1
sed
具有至少在大多数实现中y
一样工作的命令:tr
$ echo 'foobartest' | sed 'y/ots/u.x/'
fuubar.ex.
这y
命令是POSIXsed
规范,所以它应该可以在任何平台上运行。
而且由于它是sed
,您可以让它用其编辑后的版本替换文件,从而免除您麻烦的临时文件业务(前提是您的实现sed
支持该-i
选项,POSIX 未指定该选项):
$ sed -i 'y/ots/u.x/' some-file.txt
目前 BSD 实施sed
实际上并不反映tr
某些极端情况下的行为
答案2
如果像你的情况一样,你要音译字符而不改变其大小(无论如何,像 GNU 这样的一些实现tr
只支持单字节字符),你可以这样做:
tr 'ots' 'u.x' < file 1<> file
也就是说,tr
覆盖文件本身。
sed -i
这比几个帐户要好:
- 它不需要额外的磁盘空间(除了一些稀疏文件,写时复制特殊情况)
- 它保留 inode 编号、所有权、权限、ACL...
- 它与符号链接一起工作正常,不会破坏硬链接
- 它不会在被杀死时留下临时文件。
一个缺点是,如果它被中断,文件最终将被翻译一半(不过,在这种情况下,您可以再次运行它来完成它)。某些sed
实现可以通过确保原始文件保持不变(除非命令成功)来正确处理该问题。