added file_stats function

This commit is contained in:
Geoffray Levasseur-Brandin
2025-06-19 14:32:29 +02:00
parent 4be2e5ea87
commit f944271488

View File

@@ -211,5 +211,130 @@ rmspc()
}
export -f rmspc
# ------------------------------------------------------------------------------
# Rename all files in current directory to replace spaces with _
# ------------------------------------------------------------------------------
file_stats()
{
local human=0 details=0 only_avg=0 only_med=0 only_count=0 only_total=0
local path="." show_all=1 ext_filter="" ext_list="" min_size="" max_size=""
local OPTIND opt
# Analyse options
while [[ "$1" =~ ^- ]]; do
case "$1" in
-H) human=1 ;;
-d) details=1 ;;
-m) only_avg=1; show_all=0 ;;
-M) only_med=1; show_all=0 ;;
-c) only_count=1; show_all=0 ;;
-t) only_total=1; show_all=0 ;;
-a) human=1; details=1 ;;
-x) ext_filter="${2#.}"; shift ;;
-X) ext_list="${2}"; shift ;;
--min) min_size="$2"; shift ;;
--max) max_size="$2"; shift ;;
--) shift; break ;;
-*) echo "Usage: file_stats [-h] [-d] [-mMctaxX --min N --max N] [path]"; return 1 ;;
esac
shift
done
[ -n "$1" ] && path="$1"
# Prepare find filters
local find_cmd=(find "$path" -type f)
# Extension simple
if [[ -n "$ext_filter" ]]; then
find_cmd+=(-iname "*.$ext_filter")
fi
# Extension liste
if [[ -n "$ext_list" ]]; then
IFS=',' read -ra exts <<< "$ext_list"
find_cmd+=('(')
for i in "${!exts[@]}"; do
[[ $i -ne 0 ]] && find_cmd+=(-o)
find_cmd+=(-iname "*.${exts[$i]}")
done
find_cmd+=(')')
fi
# Taille min/max (à évaluer en octets)
if [[ -n "$min_size" ]]; then
find_cmd+=(-size +"$(numfmt --from=iec "$min_size")"c)
fi
if [[ -n "$max_size" ]]; then
find_cmd+=(-size -"$(( $(numfmt --from=iec "$max_size") + 1 ))"c)
fi
# Exécution
"${find_cmd[@]}" -printf "%s\n" 2>/dev/null | sort -n | awk -v human="$human" -v details="$details" -v only_avg="$only_avg" -v only_med="$only_med" -v only_count="$only_count" -v only_total="$only_total" -v show_all="$show_all" -v path="$path" '
function human_readable(x) {
split("B KiB MiB GiB TiB", units)
for (i=1; x>=1024 && i<5; i++) x /= 1024
return sprintf("%.2f %s", x, units[i])
}
{
sizes[NR] = $1
total += $1
if (min == "" || $1 < min) min = $1
if (max == "" || $1 > max) max = $1
if ($1 == 0) bucket[0]++
else {
b = int(log($1)/log(1024))
bucket[b]++
}
}
END {
count = NR
if (count == 0) {
print "Aucun fichier trouvé."; exit
}
moyenne = total / count
if (count % 2 == 1)
mediane = sizes[(count + 1) / 2]
else
mediane = (sizes[count / 2] + sizes[count / 2 + 1]) / 2
function out(label, val) {
if (human) val = human_readable(val)
printf "%-20s : %s\n", label, val
}
if (only_avg) out("Taille moyenne", moyenne)
else if (only_med) out("Taille médiane", mediane)
else if (only_count) printf "Nombre de fichiers : %d\n", count
else if (only_total) out("Taille totale", total)
else {
if (show_all || human || details) {
printf "Statistiques sur \"%s\"\n", path
printf "-------------------------\n"
}
out("Nombre de fichiers", count)
out("Taille totale", total)
out("Taille moyenne", moyenne)
out("Taille médiane", mediane)
out("Taille minimale", min)
out("Taille maximale", max)
}
if (details) {
print "\nHistogramme des tailles :"
for (i = 0; i in bucket; i++) {
low = 2^i
high = 2^(i+1)
if (i == 0)
label = sprintf("%4s %4s", "0", "1K")
else
label = sprintf("%4s %4s", human_readable(low), human_readable(high))
printf "%-20s : %5d fichiers\n", label, bucket[i]
}
}
}'
}
# ------------------------------------------------------------------------------
# EOF