在Linux上使用xargs命令的详细教程
大家好,我是良许。
在使用Linux时,你是否遇到过需要将一些命令串在一起,但是其中一个命令不接受管道输入的情况呢?在这种情况下,我们就可以使用xargs命令。xargs可以将一个命令的输出作为参数发送给另一个命令。
在Linux中,所有标准的应用程序都有与之关联的三个数据流。分别是标准输入流(stdin),标准输出流(stdout)和标准错误流(stderr)。这些流通过文本来运行,我们使用文本将输入(stdin)发送到命令,然后响应(stdout)将会以文本形式显示在终端窗口上。错误消息也以文本的形式显示在终端窗口上(stderr)。
Linux和类Unix操作系统的一大功能是可以将一个命令的标准输出流传递到另一个命令的标准输入流。第一个命令不会管它的输出是否写到了终端窗口,第二个命令也不会管它的输入是否来自键盘。
虽然所有Linux命令都有三个标准流,但是并不是所有命令都接受另一个命令的标准输出作为它的标准输入流的输入。因此我们无法通过管道将输入传给这些命令。
xargs是一个使用标准数据流构建执行管道的命令。通过使用xargs命令我们可以使echo,rm和mkdir等命令接受标准输入作为它们的参数。
xargs命令
xargs接受管道输入,也可以接受来自文件的输入。xargs使用该输入作为我们指定的命令的参数。如果我们没有给xargs指定特定的命令,则默认使用echo。xargs始终生成单行输出,即使输入的数据是多行的。
假如我们使用ls的-1(每行列出一个文件)选项,则会得到一列文件名称:
$ls-1./*.sh
这一命令列出了当前目录中的Shell脚本文件。
如果我们将输出结果通过管道传递给xargs,会得到什么样的效果?
$ls-1./*.sh|xargs
可以看出来,输出以一长串文本的形式写到了终端上。由此可见,xargs可以将输出作为参数传递给其他命令。
配合wc命令使用xargs
我们可以使用xargs命令轻松地让wc命令计算多个文件中的单词数,字符数和行数
$ls*.c|xargswc
执行结果如下:
命令运行结果显示了每个文件的统计信息以及总数。
这条命令执行了以下操作:
ls列出了所有的.page文件,并将该列表传给了xargs。xargs将所有文件名传递给wc。wc将这些文件名作为命令行参数进行处理。
使用带有确认消息的xargs
我们可以使用-p(交互)选项来让xargs提示我们是否要进行下一步的操作。
如果我们通过xargs将一串文件名的字符串传递给touch命令,touch将创建这些文件。
$echo'onetwothree'|xargs-ptouch
终端上显示将要执行的命令,xargs等待我们输入y或Y,n或N并按Enter来响应。如果只按了Enter,则视为n。只有当我们当输入y或Y时才执行该命令。
我们按下y和Enter,然后使用ls用来检查文件是否已经创建。
$lsonetwothree
将xargs与多个命令一起使用
我们可以用-I(初始参数)选项来将xargs和多个命令一起使用。这一选项定义了替换字符串。在命令行中的任何出现替换字符串的位置,都会插入我们提供给xargs的值。
有点抽象,我们以一个实例来进行讲解。
我们先用tree命令查看当前目录中的子目录。该-d(directory)选项使tree命令忽略文件,只输出目录。
$tree-d
现在只有一个子目录images。
在directories.txt这个文件中,我们有一些想要创建的目录的名称。我们先用cat查看其中的内容。
$catdirectories.txt
我们把这些内容作为输入数据传给xargs,执行以下的命令:
$catdirectories.txt|xargs-I%sh-c'echo%;mkdir%'
这条命令执行了以下操作:
catdirectories.txt:将directrories.txt文件的内容(所有要创建的目录名称)传给xargs。xargs-I%:定义了替换字符串%。sh-c:启动一个新的子shell。-c(commond)让shell读取命令。'echo%;mkdir%':每个%都会被替换为xargs传过来的目录名称。echo命令打印目录名称,mkdir命令创建目录。
命令执行结果:
我们可以用tree验证已创建是否已创建了目录。
$tree-d
将文件复制到多个位置
我们可以使用xargs命令来用一个命令将文件复制到多个位置。
首先,通过管道将两个目录的名称传给xargs。并且让xargs一次只将其中一个参数传递给正在使用的命令。
想要调用cp两次,每次各使用两个目录中的一个作为命令行参数,我们可以通过将xargs的-n(maxnumber)选项设置为1来实现。
这里还使用了-v(verbose详细信息)选项,让cp反馈正在执行的操作。
$echo~/dir1/~/dir2/|xargs-n1cp-v./*.c
我们将文件复制到了两个目录,一次复制一个目录。cp反馈了详细信息,让我们看到进行了哪些操作。
删除嵌套目录中的文件
如果文件名中包含空格或者其他特殊字符(例如换行符),xargs将无法正确解释这些文件名。我们可以使用-0(空终止符)选项来解决这一问题。此时,xargs将使用null字符作为文件名最终的分隔符。
这里我们以find命令为例。find有自己的选项来处理文件名中的空格和特殊字符,即-print0(全名,空字符)选项。
$find.-name"*.png"-typef-print0|xargs-0rm-v-rf"{}"
这一命令执行了以下操作:
find.-name“*.png”:find将从当前目录中搜索名称和*.png相匹配的对象,type-f指定了只搜索文件。-print0:名称将以空字符结尾,并且保留空格和特殊字符。xargs-0:xargs也将考虑文件名以空值结尾,并且空格和特殊字符不会引起问题。rm-v-rf"{}":rm将反馈正在进行的操作(-v),递归进行操作(-r),不发送错误提示而直接删除文件(-f)。每个文件名替换"{}"。
命令执行之后,将搜索了所有子目录,删除了其中匹配的文件。
删除嵌套目录
假设我们要删除一组嵌套的子目录,先用tree进行查看。
$tree-d
$find.-name"level_one"-typed-print0|xargs-0rm-v-rf"{}"
这条命令使用find在当前目录中递归搜索,搜索的目标是名为level_one的目录,然后将目录名通过xargs传递给rm。
这个命令和前面的命令之间的区别是,搜索的项目是最顶层目录的名称,而且-typed说明要查找的目录,而不是文件。
每个目录的名称都在删除时打印出来。我们可以用tree再查看效果:
$tree-d
所有嵌套的子目录已删除了。
删除一种文件类型以外的所有文件
我们可以使用find,xargs和rm删除所有类型的文件而只保留一种我们想要保留的类型的文件。这需要提供想要保留的文件类型。
-not选项让find返回所有与搜索模式不匹配的文件名。我们此时再次使用xargs的-I(初始参数)选项。这次定义的替换字符串为{}。这和我们之前使用的替换字符串%的效果是相同的。
$find.-typef-not-name"*.sh"-print0|xargs-0-I{}rm-v{}
命令执行之后,我们再通过ls来确认结果。可以看到,目录中只剩下了与*.sh相匹配的文件。
$ls-l
使用Xargs创建压缩文件
我们可以使用find命令来搜索文件,并通过xargs将文件名传给tar命令来创建压缩文件。
我们将在当前目录中搜索*.sh文件。
$find./-name"*.sh"-typef-print0|xargs-0tar-cvzfscript_files.tar.gz
命令执行结果将列出了所有.sh文件,并创建了压缩文件。
总结
到此这篇关于如何在Linux上使用xargs命令的文章就介绍到这了,更多相关Linux上使用xargs命令内容请搜索毛票票以前的文章或继续浏览下面的相关文章希望大家以后多多支持毛票票!
声明:本文内容来源于网络,版权归原作者所有,内容由互联网用户自发贡献自行上传,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任。如果您发现有涉嫌版权的内容,欢迎发送邮件至:czq8825#qq.com(发邮件时,请将#更换为@)进行举报,并提供相关证据,一经查实,本站将立刻删除涉嫌侵权内容。