シェルでサブディレクトリ操作を実行するには?

シェルでサブディレクトリ操作を実行するには?

たとえば、n個のソートされたサブディレクトリからコマンドを実行します。ここで、nは入力です。または、その範囲を入力として使用できるサブディレクトリ範囲に対してforループをどのように実行できますか?以下のように、ここで範囲をどのように定義する必要がありますか?

for d in ["sd1"-"sd2"] do ( cd "$d" && do stuff ) done

答え1

中かっこ拡張をサポートするシェルがある場合は、中かっこ拡張を使用してください。

for d in sd{1..2}; do
    ( cd "$d" && dostuff )
done

zshksh93またはyash -o braceexpand(除く)を使用してbashこれを実行できます。

n=4
for d in sd{1..$n}; do
    ( cd "$d" && dostuff )
done

関連質問:"eval"なしで{}拡張で変数を使用できますか?

これに対するバリエーションは次のとおりです。

for (( i=1; i<=n; ++i )); do
  str="sd$i"
  ( cd ... )
done

forこれは、他のシェルでサポートされているのと同じCスタイルループですbash(まだPOSIX標準の拡張にもかかわらず)。

答え2

を使用すると、zsh次のことができます。

for d (sd<1-10>(Nn-/)) (cd $d && dostuff)
  • <1-10>1から10までの10進数を一致させるグローバル演算子。1、…と一致します。任意の量の10進数に一致させる001ことができます。<->
  • (Nn-/)グローバル予選です。
    • N一致するものがなくても失敗しません。
    • n要素を数字で並べ替えます(したがってsd10後ろにありますsd2)。
    • -/ディレクトリタイプのファイルのみを含めます(シンボルリンク解析後)。

日付がディレクトリ名でエンコードされた2つの日付の間のディレクトリを一覧表示する場合(例sd2017-08-01:)

for d (sd<->-<->-<->(Nne{'
  [[ ! $REPLY < sd2015-06-06 && ! $REPLY > sd2017-08-09 ]]'}-/))
  (cd $d && dostuff)

答え3

seq他の考えられる解決策は、可能であればコマンドを使用することです。

for i in `seq -f "sd%03.0f" 111 121`
do
( cd "$i" && do stuff )
done

答え4

グローバル拡張がソートされているため、次のことができます。

state=0
for d in *; do
   case $d in "sd1") state=1;; "sd2") break;; esac
   if [ 1 -eq "$state" ]; then
      ( cd "$d" && dostuff )
   fi
done

sd1ここでは、果実はsd2実際の例ではなく、範囲はマイナーな数値範囲で説明できないと仮定します。可能であれば使用しますロミオ・ニノフ~の解決策

Brace 拡張は非常にきれいですが、残念ながら POSIX 要件ではないため、多くの POSIX シェルに Brace 拡張がありません。

関連情報