我有一個 bash 腳本,它根據命令提示字元的輸入重命名資料夾中的檔案:
echo "Please rename and press enter" read rename
if [ -z "$rename" ]; then
printf "no caption was selected, aborting!\n"
exit 1
fi
printf "rename is $rename\n" count=1
for i in *.jpg; do
j=printf "%04d" $count
j="$rename"$j".jpg"
count=$((count + 1))
mv "$i" $j
done
fi
shift
done
如何修改此腳本,以便資料夾中的檔案根據其大小重新命名?
如果我根據大小對文件進行排序,它們在資料夾中將如下所示:
a009 978kb
a001 567kb
a003 499kb
a008 432kb
所以我想重命名生成的檔案:
a001 978kb
a002 567kb
a003 499kb
a004 432kb
答案1
像這樣的東西:
echo "Please rename and press enter"
read rename
ls |
# prepend filename with file size in bytes
parallel stat -c %s,,sep,,%n -- |
# sort by number
sort -n |
# rename to sequencenumber followed by size in bytes
parallel -q --colsep ,,sep,, mv {2} "$rename"{#}_{1}
答案2
主要技巧是替換
for i in *.jpg
和
for i in $(ls -S *.jpg)
然而,正如 Kusalananda 指出的那樣,這假定了「受過教育的」檔案名稱(沒有空格,沒有控製字元),所以這裡有一種不同的方法:
count=1
ls -S --escape *.jpg | while read f; do
n=$(printf "%04d" $count)
((count++))
mv --no-clobber "$f" "$rename$n.jpg"
done
-S
按減小檔案大小進行排序
--escape
防止嵌入換行符的名稱造成損壞
--no-clobber
防止在腳本執行兩次時覆蓋目標文件
PS Ole Tange 的答案是一種非常有效的方法,可以完成相同的任務,但除非您經常重命名數千個文件,否則您可能不會看到差異。
答案3
在zsh
外殼中:
typeset -Z 3 count=0
for name in *.jpg(.DNOL); do
count=$(( count + 1 ))
mv -i -- "$name" "a$count.jpg"
done
.jpg
這將按照從最大到最小的順序迭代當前目錄中具有檔案名稱後綴的所有常規檔案。對於每個文件,它會將其重命名為到目前為止已處理的文件的零填充整數計數aNNN.jpg
。NNN
glob限定符使用(「按長度反轉順序」)(.DNOL)
以正確的順序對符合的檔案名稱進行排序,並使用(「常規檔案和點檔案」)僅選擇常規檔案(包括隱藏名稱)。如果沒有符合的名稱(“null glob”),則會使模式擴展為空。OL
.D
N
這適用於任何zsh
已安裝的 Unix 系統上的所有有效檔案名稱。
要使用它bash
:
zsh -c 'typeset -Z 3 count=0
for name in *.jpg(.DNOL); do
count=$(( count + 1 ))
mv -i -- "$name" "a$count.jpg"
done'
如果您想將變數$rename
作為檔案名稱前綴傳遞,而不是使用a
:
zsh -c 'typeset -Z 3 count=0
for name in *.jpg(.DNOL); do
count=$(( count + 1 ))
mv -i -- "$name" "$1$count.jpg"
done' zsh "$rename"
請注意,zsh
最後一行的 不是拼字錯誤,並且 的值在腳本內$rename
使用。$1
zsh -c