天天看點

linux下find,xargs指令詳解和執行個體

在我們平時的系統管理中,查找檔案是時常需要的一個操作,在Linux系統中有2個指令是必須要掌握的,如果我們真正掌握了這個指令已經他的常用參數的話,我們可以在工作中遊刃有餘,下面是我在網上找到的一點資料,這些天放假有空,整理出來給大家共享下,附件是壓縮的源檔案,希望大家喜歡,願和大家一起進步。。。

使用find和xargs

有時可能需要在系統中查找具有某一特征的檔案(例如檔案權限、檔案屬主、檔案長度、檔案類型等等)。這樣做可能有很多原因。可能出于安全性的考慮,或是一般性的系統管理任務,或許隻是為了找出一個不知儲存在什麼地方的檔案。F i n d是一個非常有效的工具,它可以周遊目前目錄甚至于整個檔案系統來查找某些檔案或目錄。

在本章中,我們介紹以下内容:

• find指令選項。

• 使用f i n d指令不同選項的例子。

• 配合f i n d使用x a rg s指令的例子。

由于f i n d具有如此強大的功能,是以它的選項也很多,其中大部分選項都值得我們花時間

來了解一下。即使系統中含有網絡檔案系統( N F S ),f i n d指令在該檔案系統中同樣有效,隻要你具有相應的權限。

在運作一個非常消耗資源的f i n d指令時,很多人都傾向于把它放在背景執行,因為周遊一個大的檔案系統可能會花費很長的時間(這裡是指3 0 G位元組以上的檔案系統)。

F i n d指令的一般形式為:

find pathname -options [-print -exec -ok]

讓我們來看看該指令的參數:

pathname find指令所查找的目錄路徑。例如用.來表示目前目錄,用/來表示系統根目錄。

-print find指令将比對的檔案輸出到标準輸出。

-exec find指令對比對的檔案執行該參數所給出的s h e l l指令。相應指令的形式為' c o m m -

and' {} \;,注意{ }和\;之間的空格。

-ok 和- e x e c的作用相同,隻不過以一種更為安全的模式來執行該參數所給出的s h e l l指令,

在執行每一個指令之前,都會給出提示,讓使用者來确定是否執行。

 find指令選項

f i n d指令有很多選項或表達式,每一個選項前面跟随一個橫杠-。讓我們先來看一下該命

令的主要選項,然後再給出一些例子。

-name 按照檔案名查找檔案。

-perm 按照檔案權限來查找檔案。

-prune 使用這一選項可以使f i n d指令不在目前指定的目錄中查找,如果同時使用了- d e p t h

選項,那麼- p r u n e選項将被f i n d指令忽略。

-user 按照檔案屬主來查找檔案。

-group 按照檔案所屬的組來查找檔案。

-mtime -n +n 按照檔案的更改時間來查找檔案, - n表示檔案更改時間距現在n天以内,+ n

表示檔案更改時間距現在n天以前。F i n d指令還有- a t i m e和- c t i m e選項,但它們都和- m t i m e選項

相似,是以我們在這裡隻介紹- m t i m e選項。

-nogroup 查找無有效所屬組的檔案,即該檔案所屬的組在/ e t c / g r o u p s中不存在。

-nouser 查找無有效屬主的檔案,即該檔案的屬主在/ e t c / p a s s w d中不存在。

-newer file1 ! file2 查找更改時間比檔案f i l e 1新但比檔案f i l e 2舊的檔案。

-type 查找某一類型的檔案,諸如:

b - 塊裝置檔案。

d - 目錄。

c - 字元裝置檔案。

p - 管道檔案。

l - 符号連結檔案。

f - 普通檔案。

-size n[c] 查找檔案長度為n塊的檔案,帶有c時表示檔案長度以位元組計。

-depth 在查找檔案時,首先查找目前目錄中的檔案,然後再在其子目錄中查找。

-fstype 查找位于某一類型檔案系統中的檔案,這些檔案系統類型通常可以在配置檔案

/ e t c / f s t a b中找到,該配置檔案中包含了本系統中有關檔案系統的資訊。

-mount 在查找檔案時不跨越檔案系統m o u n t點。

-follow 如果f i n d指令遇到符号連結檔案,就跟蹤至連結所指向的檔案。

-cpio 對比對的檔案使用c p i o指令,将這些檔案備份到錄音帶裝置中。

使用name選項

檔案名選項是f i n d指令最常用的選項,要麼單獨使用該選項,要麼和其他選項一起使用。

可以使用某種檔案名模式來比對檔案,記住要用引号将檔案名模式引起來。

不管目前路徑是什麼,如果想要在自己的根目錄$ H O M E中查找檔案名符合* . t x t的檔案,

使用~作為' p a t h n a m e參數,波浪号~代表了你的$ H O M E目錄。

$ find ~ -name "*.txt" -print

想要在目前目錄及子目錄中查找所有的‘ * . t x t’檔案,可以用:

$ find . -name "*.txt" -print

想要的目前目錄及子目錄中查找檔案名以一個大寫字母開頭的檔案,可以用:

$ find . -name "[A-Z]*" -print

想要在/ e t c目錄中查找檔案名以h o s t開頭的檔案,可以用:

$ find /etc -name "host*" -print

想要查找$ H O M E目錄中的檔案,可以用:

$ find ~ -name "*" -pri或ntf ind . -print

要想讓系統高負荷運作,就從根目錄開始查找所有的檔案。如果希望在系統管理者那裡

保留一個好印象的話,最好在這麼做之前考慮清楚!

$ find / -name "*" -print

如果想在目前目錄查找檔案名以兩個小寫字母開頭,跟着是兩個數字,最後是* . t x t的檔案,下面的指令就能夠傳回名為a x 3 7 . t x t的檔案:

$ find . -name "[a-z][a-z][0--9][0--9].txt" -print

 使用perm選項

如果希望按照檔案權限模式來查找檔案的話,可以采用- p e r m選項。你可能需要找到所有

使用者都具有執行權限的檔案,或是希望檢視某個使用者目錄下的檔案權限類型。在使用這一選

項的時候,最好使用八進制的權限表示法。

為了在目前目錄下查找檔案權限位為7 5 5的檔案,即檔案屬主可以讀、寫、執行,其他用

戶可以讀、執行的檔案,可以用:

$ find . -perm 755 -print

如果希望在目前目錄下查找所有使用者都可讀、寫、執行的檔案(要小心這種情況),我們

可以使用f i n d指令的- p e r m選項。在八進制數字前面要加一個橫杠-。在下面的指令中- p e r m代

表按照檔案權限查找,而‘ 0 0 7’和你在c h m o d指令的絕對模式中所采用的表示法完全相同。

$ find . -perm -007 -print

忽略某個目錄

如果在查找檔案時希望忽略某個目錄,因為你知道那個目錄中沒有你所要查找的檔案,

那麼可以使用- p r u n e選項來指出需要忽略的目錄。在使用- p r u n e選項時要當心,因為如果你同

時使用了- d e p t h選項,那麼- p r u n e選項就會被f i n d指令忽略。

如果希望在/ a p p s目錄下查找檔案,但不希望在/ a p p s / b i n目錄下查找,可以用:

$ find /apps -name "/apps/bin" -prune -o -print

 使用user和nouser選項

如果希望按照檔案屬主查找檔案,可以給出相應的使用者名。例如,在$ H O M E目錄中查找

檔案屬主為d a v e的檔案,可以用:

$ find ~ -user dave -print

在/ e t c目錄下查找檔案屬主為u u c p的檔案:

$ find /etc -user uucp -print

為了查找屬主帳戶已經被删除的檔案,可以使用- n o u s e r選項。這樣就能夠找到那些屬主

在/ e t c / p a s s w d檔案中沒有有效帳戶的檔案。在使用- n o u s e r選項時,不必給出使用者名; f i n d指令

能夠為你完成相應的工作。例如,希望在/ h o m e目錄下查找所有的這類檔案,可以用:

$ find /home -nouser -print

使用group和nogroup選項

就像u s e r和n o u s e r選項一樣,針對檔案所屬于的使用者組, f i n d指令也具有同樣的選項,為

了在/ a p p s目錄下查找屬于a c c t s使用者組的檔案,可以用:

$ find /apps -group accts -print

要查找沒有有效所屬使用者組的所有檔案,可以使用n o g r o u p選項。下面的f i n d指令從檔案

系統的根目錄處查找這樣的檔案

$ fine/-nogroup-print

按照更改時間查找檔案

如果希望按照更改時間來查找檔案,可以使用m t i m e選項。如果系統突然沒有可用空間了,

很有可能某一個檔案的長度在此期間增長迅速,這時就可以用m t i m e選項來查找這樣的檔案。

用減号-來限定更改時間在距今n日以内的檔案,而用加号+來限定更改時間在距今n日以前的

檔案。

希望在系統根目錄下查找更改時間在5日以内的檔案,可以用:

$ find / -mtime -5 -print

為了在/ v a r / a d m目錄下查找更改時間在3日以前的檔案,可以用:

$ find /var/adm -mtime +3 -print

查找比某個檔案新或舊的檔案

如果希望查找更改時間比某個檔案新但比另一個檔案舊的所有檔案,可以使用- n e w e r選

項。它的一般形式為:

newest_file_name ! oldest_file_name

其中,!是邏輯非符号。

這裡有兩個檔案,它們的更改時間大約相差兩天。

下面給出的f i n d指令能夠查找更改時間比檔案a g e . a w k新但比檔案b e l t s . a w k舊的檔案:

如果想使用f i n d指令的這一選項來查找更改時間在兩個小時以内的檔案,除非有一個現成的檔案其更改時間恰好在兩個小時以前,否則就沒有可用來比較更改時間的檔案。為了解決這一問題,可以首先建立一個檔案并将其日期和時間戳設定為所需要的時間。這可以用t o u c h指令來實作。

假設現在的時間是2 3 : 4 0,希望查找更改時間在兩個小時以内的檔案,可以首先建立這樣一個檔案:一個符合要求的檔案已經被建立;這裡我們假設今天是五月四日,而該檔案的更改時間是2 1 : 4 0,比現在剛好早兩個小時。

現在我們就可以使用f i n d指令的- n e w e r選項在目前目錄下查找所有更改時間在兩個小時以内的檔案:

$ find . -newer dstamp -print

使用type選項

U N I X或L I N U X系統中有若幹種不同的檔案類型,這部分内容我們在前面的章節已經做了介紹,這裡就不再贅述。如果要在/ e t c目錄下查找所有的目錄,可以用:

$ find /etc -type d -print

為了在目前目錄下查找除目錄以外的所有類型的檔案,可以用:

$ find . ! -type d -print

為了在/ e t c目錄下查找所有的符号連結檔案,可以用:

$ find /etc -type l -print

使用size選項

可以按照檔案長度來查找檔案,這裡所指的檔案長度既可以用塊( b l o c k)來計量,也可以用位元組來計量。以位元組計量檔案長度的表達形式為N c;以塊計量檔案長度隻用數字表示即可。

就我個人而言,我總是使用以位元組計的方式,在按照檔案長度查找檔案時,大多數人都喜歡使用這種以位元組表示的檔案長度,而不用塊的數目來表示,除非是在檢視檔案系統的大小,因為這時使用塊來計量更容易轉換。

為了在目前目錄下查找檔案長度大于1 M位元組的檔案,可以用:

$ find . -size +1000000c -print

為了在/ h o m e / a p a c h e目錄下查找檔案長度恰好為1 0 0位元組的檔案,可以用:

$ find /home/apache -size 100c -print

為了在目前目錄下查找長度超過1 0塊的檔案(一塊等于5 1 2位元組),可以用:

$ find . -size +10 -print

使用depth選項

在使用f i n d指令時,可能希望先比對所有的檔案,再在子目錄中查找。使用d e p t h選項就

可以使f i n d指令這樣做。這樣做的一個原因就是,當在使用f i n d指令向錄音帶上備份檔案系統時,

希望首先備份所有的檔案,其次再備份子目錄中的檔案。

在下面的例子中, f i n d指令從檔案系統的根目錄開始,查找一個名為C O N . F I L E的檔案。

它将首先比對所有的檔案然後再進入子目錄中查找。

$ find / -name "CON.FILE" -depth -print

 使用mount選項

在目前的檔案系統中查找檔案(不進入其他檔案系統),可以使用f i n d指令的m o u n t選項。

在下面的例子中,我們從目前目錄開始查找位于本檔案系統中檔案名以X C結尾的檔案:

$ find . -name "*.XC" -mount -print

使用cpio選項

c p i o指令可以用來向錄音帶裝置備份檔案或從中恢複檔案。可以使用f i n d指令在整個檔案系

統中(更多的情況下是在部分檔案系統中)查找檔案,然後用c p i o指令将其備份到錄音帶上。

如果希望使用c p i o指令備份/ e t c、/ h o m e和/ a p p s目錄中的檔案,可以使用下面所給出的指令,不過要記住你是在檔案系統的根目錄下:

(在上面的例子中,第一行末尾的\告訴s h e l l指令還未結束,忽略\後面的回車。)

在上面的例子中,應當注意到路徑中缺少/。這叫作相對路徑。之是以使用相對路徑,是因為在從錄音帶中恢複這些檔案的時候,可以選擇恢複檔案的路徑。例如,可以将這些檔案先恢複到另外一個目錄中,對它們進行某些操作後,再恢複到原始目錄中。如果在備份時使用了絕對路徑,例如/ e t c,那麼在恢複時,就隻能恢複到/ e t c目錄中去,别無其他選擇。在上面的例子中,我告訴f i n d指令首先進入/ e t c目錄,然後是/ h o m e和/ a p p s目錄,先比對這些目錄下的檔案,然後再比對其子目錄中的檔案,所有這些結果将通過管道傳遞給c p i o指令進行備份。

順便說一下,在上面的例子中c p i o指令使用了C 6 5 5 3 6選項,我本可以使用B選項,不過這

樣每塊的大小隻有5 1 2 位元組,而使用了C 6 5 5 3 6 選項後,塊的大小變成了6 4 K 位元組

(6 5 5 3 6 / 1 0 2 4)。

使用exec或ok來執行shell指令

當比對到一些檔案以後,可能希望對其進行某些操作,這時就可以使用- e x e c選項。一旦f i n d指令比對到了相應的檔案,就可以用- e x e c選項中的指令對其進行操作(在有些作業系統中隻允許- e x e c選項執行諸如l s或ls -l這樣的指令)。大多數使用者使用這一選項是為了查找舊檔案并删除它們。這裡我強烈地建議你在真正執行r m指令删除檔案之前,最好先用l s指令看一下,确認它們是所要删除的檔案。

e x e c選項後面跟随着所要執行的指令,然後是一對兒{ },一個空格和一個\,最後是一個分号。

為了使用e x e c選項,必須要同時使用p r i n t選項。如果驗證一下f i n d指令,會發現該指令隻輸出從目前路徑起的相對路徑及檔案名。

為了用ls -l指令列出所比對到的檔案,可以把ls -l指令放在f i n d指令的- e x e c選項中,例如:

上面的例子中,f i n d指令比對到了目前目錄下的所有普通檔案,并在- e x e c選項中使用ls -l

指令将它們列出。

為了在/ l o g s目錄中查找更改時間在5日以前的檔案并删除它們,可以用:

$ find logs -type f -mtime +5 -exec rm {} \;

記住,在s h e l l中用任何方式删除檔案之前,應當先檢視相應的檔案,一定要小心!

當使用諸如m v或r m指令時,可以使用- e x e c選項的安全模式。它将在對每個比對到的檔案進行操作之前提示你。在下面的例子中, f i n d指令在目前目錄中查找所有檔案名以. L O G結尾、更改時間在5日以上的檔案,并删除它們,隻不過在删除之前先給出提示。

按y鍵删除檔案,按n鍵不删除。

任何形式的指令都可以在- e x e c選項中使用。在下面的例子中我們使用g r e p指令。

首先比對所有檔案名為“ p a s s w d *”的檔案,例如p a s s w d、p a s s w d . o l d、p a s s w d . b a k,然後執行g r e p指令看看在這些檔案中是否存在一個r o u n d e r使用者。

find指令的例子

我們已經介紹了f i n d指令的基本選項,下面給出f i n d指令的一些其他的例子。

為了比對$ H O M E目錄下的所有檔案,下面兩種方法都可以使用:

$ find $HOME -print

$ find ~ -print

為了在目前目錄中查找s u i d置位,檔案屬主具有讀、寫、執行權限,并且檔案所屬組的用

戶和其他使用者具有讀和執行的權限的檔案,可以用:

$ find . -type f -perm 4755 -print

為了查找系統中所有檔案長度為0的普通檔案,并列出它們的完整路徑,可以用:

$ find / -type f -size 0 -exec ls -l {} \;

為了查找/ v a r / l o g s目錄中更改時間在7日以前的普通檔案,并删除它們,可以用:

$ find /var/logs -type f -mtime +7 -exec rm {} \;

為了查找系統中所有屬于a u d i t組的檔案,可以用:

$find /-name -group audit -print

我們的一個審計系統每天建立一個審計日志檔案。日志檔案名的最後含有數字,這樣我們一眼就可以看出哪個檔案是最新的,哪個是最舊的。A d m i n . l o g 檔案編上了序号:

a d m i n . l o g . 0 0 1、a d m i n . l o g . 0 0 2等等。下面的f i n d指令将删除/ l o g s目錄中通路時間在7日以前、含有數字字尾的a d m i n . l o g檔案。該指令隻檢查三位數字,是以相應日志檔案的字尾不要超過9 9 9。

$ find /logs -name 'admin.log[0-9][0-9]'[-0a-t9i]me +7 -exec rm {} \;

為了查找目前檔案系統中的所有目錄并排序,可以用:

$ find . -type d -print -local -mount |sort

為了查找系統中所有的r m t錄音帶裝置,可以用:

$ find /dev/rmt -print

xargs

在使用f i n d指令的- e x e c選項處理比對到的檔案時, f i n d指令将所有比對到的檔案一起傳遞給e x e c執行。不幸的是,有些系統對能夠傳遞給e x e c的指令長度有限制,這樣在f i n d指令運作幾分鐘之後,就會出現溢出錯誤。錯誤資訊通常是“參數列太長”或“參數列溢出”。這就是x a rg s指令的用處所在,特别是與f i n d指令一起使用。F i n d指令把比對到的檔案傳遞給x a rg s指令,而x a rg s指令每次隻擷取一部分檔案而不是全部,不像- e x e c選項那樣。這樣它可以先處理最先擷取的一部分檔案,然後是下一批,并如此繼續下去。在有些系統中,使用- e x e c選項會為處理每一個比對到的檔案而發起一個相應的程序,并非将比對到的檔案全部作為參數一次執行;這樣在有些情況下就會出現程序過多,系統性能下降的問題,因而效率不高;而使用 a rg s指令則隻有一個程序。另外,在使用x a rg s指令時,究竟是一次擷取所有的參數,還是分批取得參數,以及每一次擷取參數的數目都會根據該指令的選項及系統核心中相應的可調參數來确定。

讓我們來看看x a rg s指令是如何同f i n d指令一起使用的,并給出一些例子。

下面的例子查找系統中的每一個普通檔案,然後使用x a rg s指令來測試它們分别屬于哪類

檔案:

下面的例子在整個系統中查找記憶體資訊轉儲檔案(core dump) ,然後把結果儲存到

/tmp/core.log 檔案中:

$ find . -name "core" -print | xargs echo "" >/tmp/core.log

下面的例子在/ a p p s / a u d i t目錄下查找所有使用者具有讀、寫和執行權限的檔案,并收回相應的寫權限:

$ find /apps/audit -perm -7 -print | xargs chmod o-w

在下面的例子中,我們用g r e p指令在所有的普通檔案中搜尋d e v i c e這個詞:

$ find / -type f -print | xargs grep "device"

在下面的例子中,我們用g r e p指令在目前目錄下的所有普通檔案中搜尋D B O這個詞:

$ find . -name *\-type f -print | xargs grep "DBO"

注意,在上面的例子中, \用來取消f i n d指令中的*在s h e l l中的特殊含義。

小結

f i n d指令是一個非常優秀的工具,它可以按照使用者指定的準則來比對檔案。使用e x e c和x a rg s可以使使用者對所比對到的檔案執行幾乎所有的指令。

<a href="http://down.51cto.com/data/2354164" target="_blank">附件:http://down.51cto.com/data/2354164</a>

本文轉自你是路人甲還是霍元甲部落格51CTO部落格,原文連結http://blog.51cto.com/world77/209125如需轉載請自行聯系原作者

world77