ディレクトリは一日中多数のファイルを受け取ります。 2行目の内容に基づいてファイルを選択して移動したいと思います。 2行目は次のとおりです。
L054 EL621306DEM-A0-AGI378-0001 70807 201708072017081100061542364673600268
- 条件1:列8と9 = EL
- 条件 2: 列 42/43/44/45 = 2017
( ksh
AIX 7.1 で使用)
答え1
GNUツールの使用(GNUシェルまたはkshをサポートする他のシェル)プロセスの交換(<(...)
)、GNU xargs
、またはFreeBSDに似た互換性(-a
、、、)、GNU (、、)、GNU (他の-r
実装でもサポートされています。サポートされていない場合は無視されますが、効率は低下します):-0
mv
-t
awk
nextfile
xargs -r0a <(
find dir -type f -exec awk 'FNR == 2 {
if (substr($0, 8, 2) == "EL" && substr($0, 42, 4) == "2017")
printf "%s\0", FILENAME
nextfile}' {} +) echo mv -it /somewhere
echo
(満足すれば削除)
GNU以外のシステムでは、次のように変更できます。
{
find dir -type f -exec awk -v q="'" '
function quote_for_xargs(s) {
gsub(q, q "\\" q q, s)
gsub("\n", q "\\\n" q, s)
return q s q
}
FNR == 2 {
if (substr($0, 8, 2) == "EL" && substr($0, 42, 4) == "2017")
print quote_for_xargs(FILENAME)
nextfile
}' {} + | xargs sh -c '
[ "$#" -eq 0 ] || exec echo mv -i "$@" /somewhere <&3 3<&-' sh
} 3<&0
(満足したら削除してくださいecho
)。
つまり、find
すべてのテキストファイルへの呼び出しがあります。awk
で各ファイルのawk
2行目(FNR==2
)の条件が満たされると、ファイル名が適切な形式で印刷されますxargs
(xargs入力は、単一引用符、二重引用符、およびバックスラッシュを使用してスペースまたは改行文字で区切られた単語のリストとして扱われます。 )。区切り文字または互いをエスケープするために使用できます。たとえば、名前付き./That's tough.log
ファイルは'./That'\''s tough.log'
。
xargs
できるだけ多くの引数をに渡すには、この入力を許可します。ターゲットディレクトリは最後の引数である必要があるため、ラッパーがsh
必要です。ファイルが同じディレクトリにあるため、同じ名前の2つのファイルを別のディレクトリに移動すると、データが失われる可能性があるため、sh
これが必要です。-i
私たちに必要なmv
標準入力(-i
プロンプト用)いいえはから来るパイプfind
なので、一時fd 3を使用して外部標準入力をsh
forに渡して標準入力をsh
設定します。mv