2

プログラムでfindコマンドを作成しています:

find  "${SRC_DIR}" "${FILE_NAMES}" -type f -mtime +14 -level 0

FILE_NAMES は、照合する必要があるファイル パターンです。これは、単純な空白で区切られたパターンのリスト (*.txt、*.html など) です。

このリストを find コマンドで正しくフォーマットするには、単なるリストではなく、次のようにする必要があります。

-name *.txt -o -name *.html

私の解決策は次を使用することでした:

FILE_NAMES=$(echo ${FILES} | sed -e 's/\s+/-o -name /g')

しかし、それは機能していません。具体的には、空白を置き換えたいことを理解していないようです。誰かがこれを行うためのより良い方法を持っていますか?

4

3 に答える 3

1

すべての sed がスペースや数字などの perl のようなプレース ホルダーをサポートしているわけではありません。正確なケースをテストする方法はありませんが、以下は良いガイドになるはずです。

find -predicate -predicate ....また、デフォルトでANDされることに注意してください。作業を行うには-o、すべてを( (parens) )AND で囲む必要があるため、シェルは括弧をサブシェルの起動要求として認識しません。括弧をエスケープする必要があります\( .... -o .... \)。それが私たちを導く

 set -vx; SRC_DIR="." ; FILE_NAMES="a b c"
 find  "${SRC_DIR}" \( $(echo "$FILE_NAMES"| sed 's/ / -o -name /g;s/^/-name /') \) -type f -mtime +14 -level 0

出力

+ echo 'a b c'
+ sed 's/ / -o -name /g;s/^/-name /'
+ find . '\( -name a -o -name b  -o -name c \)' -type f -mtime +14 -level 0
find: invalid predicate `-level'

これは、私の検索が -level もサポートしていないことを示しています。

編集により、周囲の余分な"文字が削除されました\(....\)

また

ksh93 を使用している場合は、次のような変数修飾子を使用できる可能性があります。

${FILE_NAME// / -o -name}

ただし、開始部分を連結するか-name、保存された FILE_NAME の値に対して 2 番目の置換を行う必要があります。

次のコマンドを発行すると、ksh93 があるかどうかを確認できます。

echo ${.sh.version}

値が得られれば、ksh93 を持っています。

IHTH

于 2012-08-30T21:52:22.153 に答える
1

ksh:

FILES='*.txt *.html'
FILE_NAMES=$(
  # $() runs this script in a subshell
  conjunction=""
  set -f   # turn off file pattern expansion
  for patt in $FILES; do
    printf "%s -name '%s' " "$conjunction" "$patt"
    conjunction="-o"
  done
)
find  "${SRC_DIR}" ${FILE_NAMES} -type f -mtime +14 -level 0

引用符で囲まれていない$FILE_NAMESことに注意してください。シェルに変数を別々の単語に分割させたいと考えています。

于 2012-08-30T23:17:07.177 に答える
0

別のアプローチを取る方が簡単かもしれません:

find ${SRC_DIR} -type f -mtime +14 | egrep '\.(txt|html)$'

-level 0それが何のためにあるのかわからないので、ビットを省略しました-手元にあるバージョンには存在しません。いつでも元に戻すことができます...

于 2012-08-30T21:35:04.653 に答える