2015-10-22 66 views
0

我可能在我的腦海裏。我正在嘗試創建一個bash腳本,用於識別以5位數字開頭的文件,檢查該匹配文件(或文件組)是否存在目錄並將文件移動到目錄中。如果該目錄不存在,我想創建它,然後移動這些文件。比較數組和創建目錄

這是我到目前爲止的劇本,但實際上它並不遙遠。

476B Oct 19 14:43 . 
544B Oct 21 10:36 .. 
68B Sep 17 08:14 12345/ 
68B Sep 17 08:14 12735/ 
    0B Sep 17 08:14 29375.pdf 
    0B Sep 17 08:14 29375a.pdf 
    0B Sep 17 08:14 29375-1.pdf 
    0B Sep 17 08:14 32952.pdf 
    0B Sep 17 08:14 39472.pdf 
68B Sep 17 08:14 59723/ 
    0B Sep 17 08:14 97132.pdf 
273B Oct 19 14:43 sort.sh  

所以打算關閉這個例子,我想找出開頭的文件29375,並建立一個目錄,對他們來說:一個目錄,需要進行排序應該是這樣的

#!/bin/bash 

files=($(find . -type f | grep -E "[0-9]{5}" -o)) 
directories=($(find . -type d)) 

for i in ${files[*]} 
do 
    printf "▸ ▸ pdf file found: %s\n" $i 
done 

for d in ${directories[*]} 
do 
printf "▸ ▸ directory found: %s\n" $d 
done 

NewDir=(`echo ${files[@]} ${directories[@]} | tr ' ' '\n' | sort | uniq -u `) 

for nd in ${NewDir[*]} 
do 
    printf "mkdir for: %s\n" $nd 
done 

例,然後將它們移動到該目錄中。

這是我遇到麻煩的地方,比較找到的文件和存在的目錄。 NewDir數組是我在嘗試搜索此解決方案時進行的一項測試。

感謝提供反饋/幫助。

回答

1

如果我正確理解你的問題,這樣做的工作,而無需使用數組:

for dir in $(find -E . -type f -regex ".*/[[:digit:]]{5}.*" \ 
       | sed -E '[email protected]\./([0-9]{5}).*@\[email protected]' | sort -u) ; do 
    if [ ! -d "$dir" ] ; then 
     mkdir "$dir" 
    fi 
    if [ ! -d "$dir" ] ; then 
     continue 
    fi 
    find -E . -type f -regex ".*/$dir.*" -exec mv \{\} $dir \; 
done 

根據目錄的數量,則可能需要將其轉換爲使用while循環消費輸出爲find -E . -type f -regex ".*/[[:digit:]]{5}.*" | sed -E '[email protected]\./([0-9]{5}).*@\[email protected]' | sort -u,如同目前的形式,後者可能會超過可接受的長度。

編輯:請注意,-regex實際上是一個GNU查找擴展,所以當GNU的發現是在PATH

+0

謝謝你找到的第一個find它只會工作。試圖找出sed在做什麼,但除此之外,腳本做的事情很奇怪。單獨測試find命令會產生正確的結果。但是,當if語句檢查$ dir時,它會使用整個文件名(帶擴展名),而不是find命令的結果。添加一些printf進行調試,發生這種情況: 找到文件:./11111-1.jpg 檢查目錄是否存在... 找不到目錄。製作:.11111-1.jpg mkdir:./11111-1.jpg:文件存在 目錄是否存在?....是。 so..if [! -d $ dir]正在尋找目錄? – Martin

+0

管道中的'sed'命令完全可以避免這種情況。你確定你沒有錯過任何東西嗎?它的功能是(每個輸入行):捕獲5個數字後面的'。/'並輸出該捕獲。 –