目錄
為什麼要用xargs,問題的來源
xargs是什么,与管道有什么不同
1. -d 选项
2. -p 选项
3. -n 选项
4. -E 选项,有的系统的xargs版本可能是-e  eof-str
首頁 運維 linux運維 關於Linux下xargs命令詳解以及xargs與管道的區別

關於Linux下xargs命令詳解以及xargs與管道的區別

Jun 07, 2017 am 10:04 AM

為什麼要用xargs,問題的來源

在工作中經常會接觸到xargs命令,特別是在別人寫的腳本裡面也經常會遇到,但是卻很容易與管道搞混淆,本篇會詳細講解到底什麼是xargs命令,為什麼要用xargs命令以及與管道的區別。為什麼要用xargs呢,我們知道,linux指令可以從兩個地方讀取要處理的內容,一個是透過命令列參數,一個是標準輸入。例如cat、grep就是這樣的指令,舉個例子:

echo 'main' | cat test.cpp
登入後複製

這種情況下cat會輸出test.cpp的內容,而不是'main'字串,如果test. cpp不存在則cat指令報告該檔案不存在,並不會嘗試從標準輸入中讀取。 echo 'main' | 會透過管道將echo 的標準輸出(也就是字串'main')導入到cat 的標準輸入,也就是說此時cat的標準輸入中是有內容的,其內容就是字串' main'但是上面的內容中cat不會從它的標準輸入中讀入要處理的內容。 (註:標準輸入是有一個緩衝區的,就像我們在程式中使用scanf函數從標準輸入讀取一樣,實際上是從標準輸入的緩衝區中讀取的)。其實基本上linux的命令中很多的命令的設計是先從命令列參數中取得參數,然後從標準輸入中讀取,反映在程式上,命令列參數是透過main函數的int main(int argc,char *argv[]) 函數參數所獲得的,而標準輸入則是透過標準輸入函數例如C語言中的scanf讀取到的。他們獲取的地方是不一樣的。例如:

echo 'main' | cat
登入後複製

這條指令會中cat會從其標準輸入中讀取內容並處理,也就是會輸出 'main' 字串。 echo指令將其標準輸出的內容 'main' 透過管道定向到 cat 的標準輸出。

cat
登入後複製

如果僅輸入cat並回車,則該程式會等待輸入,我們需要從鍵盤輸入要處理的內容給cat,此時cat也是從標準輸入中得到要處理的內容的,因為我們的cat命令列中也沒有指定要處理的檔案名稱。大多數命令有一個參數 -  如果直接在命令的最後指定-  則表示從標準輸入中讀取,

例如:

echo 'main' | cat -
登入後複製

這樣也是可行的,會顯示'main' 字符串,同樣輸入cat - 直接回車與輸入cat 直接回車的效果也一樣,但是如果這樣呢:

echo 'main' | cat test.cpp -
登入後複製

同時指定test.cpp 和- 參數,此時cat程式還是會顯示test. cpp的內容。但是有一個程式的策略則不同,它是grep,例如:

echo 'main' | grep 'main' test.cpp -
登入後複製

該指令的輸出結果是:

test.cpp:int main()
(standard input):main
登入後複製

此時grep會同時處理標準輸入和檔案test.cpp中的內容,也就是說會在標準輸入中搜尋 'main' 也會在檔案test.cpp (該檔案名稱從grep命令列參數取得)中搜尋'main'。也就是說當命令列中 test.cpp 和 - 兩個參數同時存在的時候,不同的程式處理不同。我們看到了cat與grep處理就不同。但是有一點是一樣的 首先在命令列中查找要處理的內容的來源(是從文件還是從標準輸入,還是都有),如果在命令列中找不到與要處理的內容的來源相關的參數則預設從標準

輸入讀取要處理的內容了。

另外很多程式是不處理標準輸入的,例如 kill , rm 這些程式如果命令列參數中沒有指定要處理的內容則不會預設從標準輸入中讀取。所以:

echo '516' | kill
登入後複製

這種命裡是不能執行的。

echo 'test' | rm -f
登入後複製

這種也是沒有效果的。

這兩個指令只接受命令列參數中指定的處理內容,不從標準輸入取得處理內容。想想也很正常,kill 是結束進程,rm是刪除文件,如果要結束的進程pid和要刪除的文件名需要

從標準輸入中讀取,這個也很怪異吧。 但是像 cat與grep這些文字處理工具從標準輸入讀取待處理的內容則很自然。

但有時候我們的腳本卻需要 echo '516' | kill 這樣的效果,例如 ps -ef | grep 'ddd' | kill 這樣的效果,篩選出符合某條件的程序pid然後結束。這種需求對我們來說是理所當然而且是很常見的,那麼應該怎樣達到這樣的效果呢。有幾個解決方法:

1. 透過

kill `ps -ef | grep 'ddd'`
登入後複製

這個形式,這個時候其實等同於拼接字串得到的指令,其效果類似 kill $pid

2.

for procid in $(ps -aux | grep "some search" | awk '{print $2}'); do kill -9 $procid; done
登入後複製

其实与第一种原理一样,只不过需要多次kill的时候是循环处理的,每次处理一个

3.

 ps -ef | grep 'ddd' | xargs kill
登入後複製

OK,使用了xargs命令,铺垫了这么久终于铺到了主题上。xargs命令可以通过管道接受字符串,并将接收到的字符串通过空格分割成许多参数(默认情况下是通过空格分割) 然后将参数传递给其后面的命令,作为后面命令的命令行参数

xargs是什么,与管道有什么不同

xargs与管道有什么不同呢,这是两个很容易混淆的东西,看了上面的xargs的例子还是有点云里雾里的话,我们来看下面的例子弄清楚为什么需要xargs:

echo '--help' | cat
登入後複製

输出:

--help
echo '--help' | xargs cat
登入後複製

输出:

Usage: cat [OPTION]... [FILE]...
Concatenate FILE(s), or standard input, to standard output.
 -A, --show-all   equivalent to -vET
 -b, --number-nonblank number nonempty output lines
 -e      equivalent to -vE
 -E, --show-ends   display $ at end of each line
 -n, --number    number all output lines
 -s, --squeeze-blank  suppress repeated empty output lines
 -t      equivalent to -vT
 -T, --show-tabs   display TAB characters as ^I
 -u      (ignored)
 -v, --show-nonprinting use ^ and M- notation, except for LFD and TAB
  --help  display this help and exit
  --version output version information and exit
登入後複製

可以看到 echo '--help' | cat 该命令输出的是echo的内容,也就是说将echo的内容当作cat处理的文件内容了,实际上就是echo命令的输出通过管道定向到cat的输入了。然后cat从其标准输入中读取待处理的文本内容。这等价于在test.txt文件中有一行字符 '--help' 然后运行 cat test.txt 的效果。

而 echo '--help' | xargs cat 等价于 cat --help 什么意思呢,就是xargs将其接受的字符串 --help 做成cat的一个命令参数来运行cat命令,同样 echo 'test.c test.cpp' | xargs cat 等价于 cat test.c test.cpp 此时会将test.c和test.cpp的内容都显示出来。

xargs的一些有用的选项

相信到这里应该都知道xargs的作用了,那么我们看看xargs还有一些有用的选项:

1. -d 选项

默认情况下xargs将其标准输入中的内容以空白(包括空格、Tab、回车换行等)分割成多个之后当作命令行参数传递给其后面的命令,并运行之,我们可以使用 -d 命令指定分隔符,例如:

echo '11@22@33' | xargs echo
登入後複製

输出:

11@22@33
登入後複製

默认情况下以空白分割,那么11@22@33这个字符串中没有空白,所以实际上等价于 echo 11@22@33 其中字符串 '11@22@33' 被当作echo命令的一个命令行参数

echo '11@22@33' | xargs -d '@' echo
登入後複製

输出:

11 22 33
登入後複製

指定以@符号分割参数,所以等价于 echo 11 22 33 相当于给echo传递了3个参数,分别是11、22、33

2. -p 选项

使用该选项之后xargs并不会马上执行其后面的命令,而是输出即将要执行的完整的命令(包括命令以及传递给命令的命令行参数),询问是否执行,输入 y 才继续执行,否则不执行。这种方式可以清楚的看到执行的命令是什么样子,也就是xargs传递给命令的参数是什么,例如:

echo '11@22@33' | xargs -p -d '@' echo
登入後複製

输出:

echo 11 22 33
登入後複製

?...y ==>这里询问是否执行命令 echo 11 22 33 输入y并回车,则显示执行结果,否则不执行

11 22 33 ==>执行结果

3. -n 选项

该选项表示将xargs生成的命令行参数,每次传递几个参数给其后面的命令执行,例如如果xargs从标准输入中读入内容,然后以分隔符分割之后生成的命令行参数有10个,使用 -n 3 之后表示一次传递给xargs后面的命令是3个参数,因为一共有10个参数,所以要执行4次,才能将参数用完。例如:

echo '11@22@33@44@55@66@77@88@99@00' | xargs -d '@' -n 3 echo
登入後複製

输出结果:

11 22 33
44 55 66
77 88 99
00
登入後複製

等价于:

echo 11 22 33
echo 44 55 66
echo 77 88 99
echo 00
登入後複製

实际上运行了4次,每次传递3个参数,最后还剩一个,就直接传递一个参数。

4. -E 选项,有的系统的xargs版本可能是-e eof-str

该选项指定一个字符串,当xargs解析出多个命令行参数的时候,如果搜索到-e指定的命令行参数,则只会将-e指定的命令行参数之前的参数(不包括-e指定的这个参数)传递给xargs后面的命令

echo '11 22 33' | xargs -E '33' echo
登入後複製

输出:

11 22
登入後複製

可以看到正常情况下有3个命令行参数 11、22、33 由于使用了-E '33' 表示在将命令行参数 33 之前的参数传递给执行的命令,33本身不传递。等价于 echo 11 22 这里-E实际上有搜索的作用,表示只取xargs读到的命令行参数前面的某些部分给命令执行。

注意:-E只有在xargs不指定-d的时候有效,如果指定了-d则不起作用,而不管-d指定的是什么字符,空格也不行。

echo '11 22 33' | xargs -d ' ' -E '33' echo => 输出 11 22 33
echo '11@22@33@44@55@66@77@88@99@00 aa 33 bb' | xargs -E '33' -d '@' -p echo => 输出 11 22 33 44 55 66 77 88 99 00 aa 33 bb
## -0 选项表示以 '\0' 为分隔符,一般与find结合使用
find . -name "*.txt"
登入後複製

输出:

./2.txt
./3.txt
./1.txt     => 默认情况下find的输出结果是每条记录后面加上换行,也就是每条记录是一个新行
find . -name "*.txt" -print0
登入後複製

输出:

./2.txt./3.txt./1.txt     => 加上 -print0 参数表示find输出的每条结果后面加上 '\0' 而不是换行
find . -name "*.txt" -print0 | xargs -0 echo
登入後複製

输出:

./2.txt ./3.txt ./1.txt
find . -name "*.txt" -print0 | xargs -d '\0' echo
登入後複製

输出:

./2.txt ./3.txt ./1.txt
登入後複製

xargs的 -0 和 -d '\0' 表示其从标准输入中读取的内容使用 '\0' 来分割,由于 find 的结果是使用 '\0' 分隔的,所以xargs使用 '\0' 将 find的结果分隔之后得到3个参数: ./2.txt ./3.txt ./1.txt   注意中间是有空格的。上面的结果就等价于 echo ./2.txt ./3.txt ./1.txt

實際上使用xargs預設的空白分隔符號也是可以的  find . -name "*.txt"  | xargs  echo   因為換行符號也是xargs的預設空格符的一種。 find指令如果不加-print0其搜尋結果的每一字串後面其實是加了換行。

以上是關於Linux下xargs命令詳解以及xargs與管道的區別的詳細內容。更多資訊請關注PHP中文網其他相關文章!

本網站聲明
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn

熱AI工具

Undresser.AI Undress

Undresser.AI Undress

人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover

AI Clothes Remover

用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool

Undress AI Tool

免費脫衣圖片

Clothoff.io

Clothoff.io

AI脫衣器

AI Hentai Generator

AI Hentai Generator

免費產生 AI 無盡。

熱門文章

R.E.P.O.能量晶體解釋及其做什麼(黃色晶體)
3 週前 By 尊渡假赌尊渡假赌尊渡假赌
R.E.P.O.最佳圖形設置
3 週前 By 尊渡假赌尊渡假赌尊渡假赌
R.E.P.O.如果您聽不到任何人,如何修復音頻
3 週前 By 尊渡假赌尊渡假赌尊渡假赌
WWE 2K25:如何解鎖Myrise中的所有內容
3 週前 By 尊渡假赌尊渡假赌尊渡假赌

熱工具

記事本++7.3.1

記事本++7.3.1

好用且免費的程式碼編輯器

SublimeText3漢化版

SublimeText3漢化版

中文版,非常好用

禪工作室 13.0.1

禪工作室 13.0.1

強大的PHP整合開發環境

Dreamweaver CS6

Dreamweaver CS6

視覺化網頁開發工具

SublimeText3 Mac版

SublimeText3 Mac版

神級程式碼編輯軟體(SublimeText3)

在Linux終端中使用python --version命令時如何解決權限問題? 在Linux終端中使用python --version命令時如何解決權限問題? Apr 02, 2025 am 06:36 AM

Linux終端中使用python...

c語言多線程的四種實現方式 c語言多線程的四種實現方式 Apr 03, 2025 pm 03:00 PM

語言多線程可以大大提升程序效率,C 語言中多線程的實現方式主要有四種:創建獨立進程:創建多個獨立運行的進程,每個進程擁有自己的內存空間。偽多線程:在一個進程中創建多個執行流,這些執行流共享同一內存空間,並交替執行。多線程庫:使用pthreads等多線程庫創建和管理線程,提供了豐富的線程操作函數。協程:一種輕量級的多線程實現,將任務劃分成小的子任務,輪流執行。

web.xml怎麼打開 web.xml怎麼打開 Apr 03, 2025 am 06:51 AM

要打開 web.xml 文件,可以使用以下方法:使用文本編輯器(如記事本或 TextEdit)使用集成開發環境(如 Eclipse 或 NetBeans)使用命令行編輯命令(Windows:notepad web.xml;Mac/Linux:open -a TextEdit web.xml)

Linux系統自帶Python解釋器能刪除嗎? Linux系統自帶Python解釋器能刪除嗎? Apr 02, 2025 am 07:00 AM

關於Linux系統自帶Python解釋器的刪除問題許多Linux發行版在安裝時會預裝Python解釋器,它並非通過軟件包管理器�...

Linux最好使用的是什麼? Linux最好使用的是什麼? Apr 03, 2025 am 12:11 AM

Linux最適合用作服務器管理、嵌入式系統和桌面環境。 1)在服務器管理中,Linux用於託管網站、數據庫和應用程序,提供穩定性和可靠性。 2)在嵌入式系統中,Linux因其靈活性和穩定性被廣泛應用於智能家居和汽車電子系統。 3)在桌面環境中,Linux提供了豐富的應用和高效的性能。

Debian Hadoop 兼容性怎樣 Debian Hadoop 兼容性怎樣 Apr 02, 2025 am 08:42 AM

DebianLinux以其稳定性和安全性著称,广泛应用于服务器、开发和桌面环境。虽然目前缺乏关于Debian与Hadoop直接兼容性的官方说明,但本文将指导您如何在Debian系统上部署Hadoop。Debian系统需求:在开始Hadoop配置前,请确保您的Debian系统满足Hadoop的最低运行要求,这包括安装必要的Java运行时环境(JRE)和Hadoop软件包。Hadoop部署步骤:下载并解压Hadoop:从ApacheHadoop官方网站下载您需要的Hadoop版本,并将其解

Debian Strings能否兼容多種瀏覽器 Debian Strings能否兼容多種瀏覽器 Apr 02, 2025 am 08:30 AM

“DebianStrings”並非標準術語,其具體含義尚不明確。本文無法直接評論其瀏覽器兼容性。然而,如果“DebianStrings”指的是在Debian系統上運行的Web應用,則其瀏覽器兼容性取決於應用本身的技術架構。大多數現代Web應用都致力於跨瀏覽器兼容性。這依賴於遵循Web標準,並使用兼容性良好的前端技術(如HTML、CSS、JavaScript)以及後端技術(如PHP、Python、Node.js等)。為了確保應用與多種瀏覽器兼容,開發者通常需要進行跨瀏覽器測試,並使用響應式

使用Go語言連接Oracle數據庫時是否需要安裝Oracle客戶端? 使用Go語言連接Oracle數據庫時是否需要安裝Oracle客戶端? Apr 02, 2025 pm 03:48 PM

使用Go語言連接Oracle數據庫時是否需要安裝Oracle客戶端?在使用Go語言開發時,連接Oracle數據庫是一個常見需求�...

See all articles