2017-10-01 79 views
0

我是shell腳本的新手。我想迭代一個目錄下面的特定模式。KSH Shell腳本匹配文件模式

Ad_sf_03041500000.dat 
SF_AD_0304150.DEL 
SF_AD_0404141.EXP 

位數應與此模式完全匹配。 我正在使用KSH shell腳本。你能不能幫我迭代循環中的文件?

+1

你能否讓我知道哪種模式應該與文件名匹配?應該預期輸出什麼?你想要一個目錄中的特定文件,或者你想看所有的文件? – RavinderSingh13

+0

你說「*位數應該與這個模式*完全匹配」,但是你的第一個例子的位數與你的第二個和第三個不同。請準確地描述*有多少個字母,多少個數字以及哪些「擴展」是有效的。情況如何,這是否意義重大? – cdarke

+0

感謝您的支持我的朋友。我的文件模式是ad_sf_11digits.dat和SF_AD_7digits.EXP和SF_AD_7digits.DEL ..我給出的數字是樣本。我需要.dat文件在最後一個下劃線後應該有正好11位數字,而其他兩個文件在最後一個下劃線後應該只有7位數字 – Mani

回答

0

自動通配符生成方法。與領先的文本和行號打印文件名...

  1. POSIX外殼:

    2> /dev/null find \ 
        $(echo Ad_sf_03041500000.dat SF_AD_0304150.DEL SF_AD_0404141.EXP | 
        sed 's/[0-9]/[0-9]/g') | 
    while read f ; do 
        echo "Here's $f"; 
    done | nl 
    
  2. ksh(從Chepner借了點):

    set - Ad_sf_03041500000.dat SF_AD_0304150.DEL SF_AD_0404141.EXP 
    for f in ${*//[0-9]/[0-9]} ; do [ -f "$f" ] || continue 
        echo "Here's $f"; 
    done | nl 
    

任一方法的輸出:

 1 Here's Ad_sf_03041500000.dat 
    2 Here's SF_AD_0304150.DEL 
    3 Here's SF_AD_0404141.EXP 

如果不需要行號,請省略| nlecho可以替換爲需要在文件上運行的任何命令。


POSIX代碼如何工作。 OP規範很簡單,只需稍微調整即可生成正確的通配符。例如:

echo Ad_sf_03041500000.dat SF_AD_0304150.DEL SF_AD_0404141.EXP | 
sed 's/[0-9]/[0-9]/g' 

其輸出恰好所需的圖案(線添加爲清楚起見供稿):

Ad_sf_[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9].dat 
SF_AD_[0-9][0-9][0-9][0-9][0-9][0-9][0-9].DEL 
SF_AD_[0-9][0-9][0-9][0-9][0-9][0-9][0-9].EXP 

的圖案上面去find,打印只有匹配的文件名,(未圖案自身時沒有文件),然後文件名轉到while循環。

(該ksh變種是同樣的方法,但使用代替sedfind模式替換settest -f

+0

最有可能的OP意味着更抽象的模式,但固定的字符串也是一種模式。 – agc

+0

感謝您的支持,我的朋友@agc。我想你錯誤地理解了我的問題。我的文件模式是ad_sf_11digits.dat和SF_AD_7digits.EXP和SF_AD_7digits.DEL ..我給出的數字是樣本。我需要.dat文件應該有最後一個下劃線後的正好11位數字,其他兩個文件應該只有最後一個下劃線後的7位數字 – Mani

0

你正在尋找的模式是

Ad_sf_{11}([[:digit:]]).dat 
SF_AD_{7}([[:digit:]]).DEL 
SF_AD_{7}([[:digit:]]).EXP 

{n}(...)模式與以下模式完全匹配nksh的唯一擴展(據我所知,甚至不是zsh提供了一個等價物)。

遍歷匹配的文件,你可以使用

for f in Ad_sf_{11}(\d).dat SF_AD_{7}(\d)[email protected](DEL|EXP); do 

在那裏我已經用「挑人」運營商@(...)到兩個較短的圖案組合成一個單一的模式,我用\d,其中ksh在圓括號內支持作爲[[:digit:]]的較短版本。

+0

* Lubuntu v17.04 *,測試上述代碼在'mksh',返回:'語法錯誤: '''unexpected'。在'ksh'中測試時,循環中的echo $ f會在文件不存在時自動打印模式 - 可能是需要的,但它可能不是... – agc

+2

'mksh'是「與ksh基本兼容」的,但它不是'ksh',這就是OP聲稱使用的內容。至於沒有匹配發生時會發生什麼,這在文件名生成的手冊頁中清楚地記錄:「如果否找到與該模式相匹配的文件名,那麼該文件名的組成部分 保持不變,除非該模式的前綴爲〜(N),在這種情況下,它將按照下面的描述刪除。「 – chepner

+0

標準方法是檢查是否存在」f '實際上是一個位於循環頂部的文件:'[ -f「$ f」] || continue'。 – chepner