こんにちはスクリプトを学びに来ました。 「for」ループを使用して簡単なスクリプトを作成しようとしています。
userというフォルダに何百ものフォルダがあります。
このコマンドを実行すると、別のフォルダに移動する必要があるフォルダの一覧が表示されます。
cat failed | awk -F ":" '/FAILED/ {print $1}' | uniq
つまり、操作に失敗したユーザーの下のフォルダをusers / failed / failedusersに移動する必要があります。
私が今やっていることは、まず次のように新しいファイルを作成することです。
cat failed | awk -F ":" '/FAILED/ {print $1}' | uniq > failedusers
その後、次のコマンドを使用してフォルダを移動しました。
while read line; do cp -r users/$line users/failed; done < failedusers
私の質問はただ使用できますか?~のため出力を別のファイルに書き込み、次を使用する代わりにコマンド読みながら完了するためのコマンドですか?
たとえば、次のようにループ内の変数に値を割り当てます。
faileduser=`cat failed | awk -F ":" '/FAILED/ {print $1}' | uniq`
次に、次のように書きます。
mv users/$faileduser user/failed/$faileduser
上記の内容を作成しようとすると、さまざまなエラーが発生します。
ありがとう
答え1
GNUxargs
とkshスタイルのプロセス交換をサポートするシェルを使用すると、次のことができます。
xargs -rd '\n' -I USER -a <(awk -F : '/FAILED/ {print $1}' failed | sort -u
) cp -r users/USER user/failed/USER
これにより、zsh
次のことができます。
faileduser=( ${(f)"$(awk -F : '/FAILED/ {print $1}' failed | sort -u)"} )
autoload zargs
zargs -rI USER -- $faileduser -- cp -r users/USER user/failed/USER
コピーしたいとしましょうUSER
到着 user/failed/USER
つまり、コピーしてください。入力する user/failed
、次のこともできます(まだ使用されていますzsh
)。
(( $#faileduser )) && cp -r users/$^faileduser user/failed/
bash
シェルを使用すると、次のことができます。
readarray -t faileduser < <(awk -F : '/FAILED/ {print $1}' failed | sort -u)
(( ${#faileduser[@]} )) &&
cp -r "${faileduser[@]/#/user\/}" user/failed/
または、すべてのユーザー名の前にawk
以下を追加してください。user/
readarray -t faileduser < <(awk -F : '/FAILED/ {print "user/"$1}' failed | sort -u)
(( ${#faileduser[@]} )) &&
cp -r "${faileduser[@]}" user/failed/
ループの場合、Korn(含む、と一緒に使用することもできます)などのfor
シェルを使用すると、構文は次のようになります。bash
zsh
for user in "${faileduser[@]}"; do
cp -r "user/$user" "user/failed/$user"
done
次zsh
のように短縮できます。
for user ($faileduser) cp -r user/$user user/failed/$user
そして:
faileduser=`cat failed | awk -F ":" '/FAILED/ {print $1}' | uniq`
(`...`
は廃止され、廃止されたコマンドの代替形式です。$(...)
)
awk
出力を次の場所に保存します。スカラー、配列変数ではありません。
上記のコマンド置換で直接行ったように、引数zsh
拡張フラグを使用して改行文字に分割できます。f
array=( ${(f)faileduser} )
Bash(またはksh)では、globを無効にして分割を調整した後、分割+glob演算子を使用できます。
set -o noglob
IFS=$'\n'
array=( $faileduser )
(はい、bash
引用されていない引数拡張はBourneシェルから継承されたバグ機能であり、zshやBourneに似た最新のシェルではなく、ほとんどのシェルに存在する暗黙の分割+glob演算子(!)を呼び出します。修理)。