ダウンロード フォルダーをファイルが作成された日付で並べ替えるスクリプトを作成中です。使用しているスクリプトは次のとおりです。
#!/bin/bash
cd ~/Downloads
for FILENAME in *
do
if [[ -f $FILENAME ]]; then
date="$(ls -l $FILENAME | tr -s ' ' | cut -d ' ' -f 6 | tr -d '.')"
mkdir -vp "$date"
find . -maxdepth 1 -type f -name $FILENAME -exec mv {} "$date" \;
fi
done
cd -
このスクリプトによって作成されたフォルダーの名前は just であり、Jun
どこかで何らかの変換が行われていると考えられます。
もし私が
ls -l test0 | tr -s ' ' | cut -d ' ' -f 6 | tr -d '.'
日付は19062014
正しく表示されます。
bash -x
これはスクリプトの結果です:
sigurd@Goliath ~ -> bash -x clean
+ cd /home/sigurd/Downloads
+ for FILENAME in '*'
+ [[ -f test0 ]]
++ ls -l test0
++ tr -s ' '
++ cut -d ' ' -f 6
++ tr -d .
+ date=Jun
+ mkdir -vp Jun
mkdir: created directory 'Jun'
+ find . -maxdepth 1 -type f -name test0 -exec mv '{}' Jun ';'
+ for FILENAME in '*'
+ [[ -f test1 ]]
++ ls -l test1
++ tr -s ' '
++ cut -d ' ' -f 6
++ tr -d .
+ date=Jun
+ mkdir -vp Jun
+ find . -maxdepth 1 -type f -name test1 -exec mv '{}' Jun ';'
+ cd -
/home/sigurd
私が探している機能は、スクリプトがファイルが作成された日時に基づいて19_06_2014
、などの名前のフォルダーにファイルを移動することです。20_06_2014
答え1
のような日付形式を使用することをお勧めします2014-06-19
。 そうすれば、日付がls
時系列順に表示されます。
GNU システムの場合:
#! /bin/bash -
cd ~/Downloads &&
find . -maxdepth 1 -type f -printf '%p\0%TF\0' |
while IFS= read -rd '' file && read -d '' date; do
mkdir -vp "$date" && mv "$file" "$date"
done
zsh
どのシステムでも:
#! /bin/zsh -
zmodload zsh/stat || exit
cd ~/Downloads &&
for file (./*(ND.)) {
zstat -A date -F %F +mtime $file &&
mkdir -p $date &&
mv $file $date
}
答え2
推測ですが、ls
コマンドを対話的に実行するときに使用されるエイリアスがあり、そのエイリアスはスクリプトでは使用されていません。おそらく、次のようなものでしょうか?
alias ls="ls --full-time"
一般的な考え方では、解析を試みるのはls
悪い考えだと言われています。Linux マシンを使用している場合は、次のような方法の方が望ましいかもしれません。
stat "$FILENAME" | awk '/^Modify: /{print $2}'
編集: または、Stéphane が以下で指摘しているように、find
を と併用する-printf
とさらに良いでしょう。 の出力はstat
よりも少し予測しやすいですls
が、-printf
出力形式を完全に制御できます。
答え3
完全なコードはこちら
#!/bin/bash
cd ~/Downloads
for FILENAME in $(find . -maxdepth 1 -type f); do
DATE=$(stat "$FILENAME" | awk '/^Modify: /{print $2}')
[ ! -d "$DATE" ] && mkdir -vp "$DATE"
mv "$FILENAME" "${DATE}/$FILENAME"
done
cd -