如何执行任何命令编辑其文件(参数)“来代替”使用bash?(How do I execute any

2019-07-19 02:36发布

我有一个文件TEMP.TXT,我想用排序sort在bash命令。

我想排序的结果来替换原来的文件。

这并不为例(我得到一个空文件)工作:

sortx temp.txt > temp.txt

这可以在一个线路来完成,而不诉诸复制到临时文件?


编辑: -o选项是非常酷的sort 。 我用sort在我作为一个例子问题。 我碰到与其他命令同样的问题:

uniq temp.txt > temp.txt.

有没有更好的通用的解决方案?

Answer 1:

sort temp.txt -o temp.txt


Answer 2:

一个sort需要看到所有的输入,然后才能开始输出。 出于这个原因, sort程序可以很容易地提供一个选项来修改就地文件:

sort temp.txt -o temp.txt

具体来说, GNU的文件sort说:

通常情况下,这类读取打开输出文件,这样你就可以放心地使用像命令排序代替文件之前所有的输入sort -o FFcat F | sort -o F cat F | sort -o F 。 然而, sort--merge-m )可以读取所有输入之前打开输出文件,所以像命令cat F | sort -m -o F - G cat F | sort -m -o F - G是不是安全的排序可能会开始写Fcat做阅读它。

虽然BSD的文件sort说:

如果[中]输出文件是输入文件之一,排序和写输出给[]输出文件之前对其进行排序拷贝到一个临时文件。

命令如uniq可以开始编写输出他们读完输入之前。 这些命令通常不支持就地编辑(这将是他们很难支持此功能)。

您通常解决这个与临时文件,或者如果你绝对要避免中间文件,你可以使用一个缓冲写出来之前,完整的结果存储。 例如,用perl

uniq temp.txt | perl -e 'undef $/; $_ = <>; open(OUT,">temp.txt"); print OUT;'

在这里,perl的部分内容,从完整的输出uniq变量$_ ,然后覆盖这个数据的原始文件。 你可以做同样在您选择的脚本语言,甚至在猛砸。 但是请注意,它需要足够的内存来存储整个文件,大文件时,这是不可取的。



Answer 3:

这里有一个更通用的方法,用uniq的工作,排序和诸如此类的东西。

{ rm file && uniq > file; } < file


Answer 4:

东武对海绵评论认股权证是在自己的权利的答案。

从引用moreutils主页:

大概在moreutils最通用的工具,至今是海绵(1),它可以让你做这样的事情:

 % sed "s/root/toor/" /etc/passwd | grep -v joey | sponge /etc/passwd 

然而, sponge从同一问题的困扰史蒂夫·杰索普这里批语。 如果任何在之前的管道中的命令的sponge失败,则原始文件将被覆盖。

$ mistyped_command my-important-file | sponge my-important-file
mistyped-command: command not found

嗯,哦, my-important-file不见了。



Answer 5:

在这里你走,一条线:

sort temp.txt > temp.txt.sort && mv temp.txt.sort temp.txt

从技术上讲没有复制到一个临时文件,而“MV”命令应该是瞬间。



Answer 6:

我喜欢的sort file -o file的答案,但不想键入文件名相同的两倍。

使用bash 历史扩展 :

$ sort file -o !#^

当你按回车键抓住了当前行的第一个参数。

独特的排序就地:

$ sort -u -o file !#$

抓住当前行的最后一个ARG。



Answer 7:

许多人提到的-o选项。 这里是man页面的一部分。

从手册页:

   -o output-file
          Write output to output-file instead of to the  standard  output.
          If  output-file  is  one of the input files, sort copies it to a
          temporary file before sorting and writing the output to  output-
          file.


Answer 8:

这将是非常内存受限的,但你可以用awk中间数据存储在内存中,然后将它写回。

uniq temp.txt | awk '{line[i++] = $0}END{for(j=0;j<i;j++){print line[j]}}' > temp.txt


Answer 9:

替代sponge与更常见sed

sed -ni r<(command file) file

它适用于任何命令( sortuniqtac ,...),并采用了非常著名sed-i选项 (编辑文件就地)。

警告:尝试command file首先是因为就地编辑的文件是不是天生的安全。


说明

首先,你告诉sed不打印(原)线( -n选项 ),并与的帮助sedr命令和bash的进程替换 ,通过所产生的内容<(command file)会输出保存到位


使事情变得更简单

你可以用这个解决方案到一个函数:

ip_cmd() { # in place command
    CMD=${1:?You must specify a command}
    FILE=${2:?You must specify a file}
    sed -ni r<("$CMD" "$FILE") "$FILE"
}

$ cat file
d
b
c
b
a

$ ip_cmd sort file
$ cat file
a
b
b
c
d

$ ip_cmd uniq file
$ cat file
a
b
c
d

$ ip_cmd tac file
$ cat file
d
c
b
a

$ ip_cmd
bash: 1: You must specify a command
$ ip_cmd uniq
bash: 2: You must specify a file


Answer 10:

使用参数--output=-o

只是试图在FreeBSD:

sort temp.txt -otemp.txt


Answer 11:

要添加uniq能力,有什么不利之处:

sort inputfile | uniq | sort -o inputfile


Answer 12:

阅读上的非交互式编辑器, ex



Answer 13:

如果您坚持使用sort程序,你必须使用一个中间文件-我不认为sort对内存排序的选项。 任何其他招用标准输入/输出会失败,除非你能保证对排序的标准输入缓冲区的大小足够大,以适应整个文件。

编辑:在我身上的耻辱。 sort temp.txt -o temp.txt做工精良。



Answer 14:

另一种解决方案:

uniq file 1<> file


文章来源: How do I execute any command editing its file (argument) “in place” using bash?