Anzeigen der Größe in lesbarem Format im Befehl "find"

2

Ich versuche, die Dateigröße in einem für Menschen lesbaren Format mit dem folgenden Befehl "find" anzuzeigen

 find $BASE_DIR/ -user $USER -size +$LOWERSIZELIMIT -mtime +$MY_MTIME -type f -printf      "%s %p\n" 2> /dev/null | 
 sort -nr | 
 head -n $NUMFILES >> $TESTFILE

So sieht meine Funktion zum Auffinden großer Dateien aus. Es wird $ 1 als Argument verwendet, um den Basisverzeichnispfad an den Befehl find zu übergeben.

 function find_files {
 #echo "In find files"
 # $1 = base directory from where to start the search

 find $1/ -user $USER -size +$LOWERSIZELIMIT -mtime +$MY_MTIME -type f -printf "%s %p\n" 2> /dev/null | sort -nr | head -n $NUMFILES >> $TESTFILE

 if [[ -s $TESTFILE ]] ; 
 then 
   echo "***********************************************************************" >> $DUMPFILE
   echo "***********************************************************************" >> $DUMPFILE
   echo "***********************************************************************" >> $DUMPFILE
   echo "***********************************************************************" >> $DUMPFILE
   #cat $TESTFILE
   cat $TESTFILE >> $DUMPFILE
   rm $TESTFILE
   return 0
 else
   return 1
 fi
 }
user199889
quelle
Würdest du bitte zuerst deine Frage in Form einer Frage formulieren? :-)
Scott
$BASE_DIR/und $1/brauche keine abschließenden Schrägstriche, aber sie sollten wirklich in Anführungszeichen stehen, wie in:find "$1" -user …
Scott

Antworten:

2

Verwenden Sie die Option -exec für find (vergessen Sie nicht, mit \; zu enden). Wenn Sie nur einen Teil der Informationen aus Ihrem exec-Befehl benötigen, analysieren Sie mit awk.

find $BASE_DIR/ -user $USER -size +$LOWERSIZELIMIT -mtime +$MY_MTIME -type f -exec /bin/ls -hl {} \;

Verwenden Sie einen anderen Befehl, wenn Sie keine von Menschen lesbare Ausgabe von ls wünschen oder wenn Sie dies so tun möchten

find $BASE_DIR/ -user $USER -size +$LOWERSIZELIMIT -mtime +$MY_MTIME -type f -exec /bin/ls -hl {} \; | awk '{ print $5,$9 }'

Die schwierigsten Teile von find's exec verwenden {} als Ergebniselement für das, was gefunden wird, und der Befehl muss mit \ enden. Wenn Sie eine Befehlskette in derselben Zeile haben, die durch; Sie müssen Ihren Suchvorgang beenden und dann ein; hinzufügen. es gibt also 2, wie ein Befehl; find $ BASE_DIR / -user $ USER -size + $ LOWERSIZELIMIT -mtime + $ MY_MTIME -type f -exec / bin / ls -hl {} \ ;; irgendein Befehl;

Jon Zobrist
quelle
2
Beachten Sie bei "und der Befehl muss auf \;" , dass -exec ... +(und xargs ...) viel schneller ist als -exec ... \;. (Testen Sie sich mit dem timeBefehl, oder sehen Sie sich einen anderen Test an .)
Arjan
Vielen Dank, @Arjan. Ich hatte vorher nicht + anstelle von \ verwendet; also habe ich die manpage drauf gelesen. Der Hauptunterschied scheint darin zu liegen, dass der Befehl nicht nur einmal pro Treffer ausgeführt wird, sondern einmal mit allen Übereinstimmungen als Argumente. finden . -iname " .php" -exec php -l {} + Es wurden keine Syntaxfehler in ./1.php gefunden. -iname " .php" -exec php -l {} \; In ./1.php wurden keine Syntaxfehler festgestellt. In ./2.php wurden keine Syntaxfehler festgestellt. -Typ f -exec / bin / ls -hl {} + | awk '{print $ 5, $ 9}' 17 ./1.php 17 ./2.php find. -Typ f -exec / bin / ls -hl {} \; | awk '{print $ 5, $ 9}' 17 ./1.php 17 ./2.php
Jon Zobrist
Ich habe den folgenden Befehl ausprobiert, aber es ergab ein etwas anderes Ergebnis. Es gab eine Liste mit großen Dateien, aber es wurden noch größere Dateien übersehen. find / proj / platform_emulation3 / kv / cp / -user $ USER -size + 3000k -mtime +3 -exec / bin / ls -hl {} \; | awk '{print $ 5, $ 9}' | sort -nr | head -n 5
user199889
2

Die Subtilität ist hier das sort, kann man nicht (leicht und korrekt) sortieren Menschen lesbaren Zahlen (es sei denn , Sie haben sortvon GNU coreutils > = 7.5, unterstützt eine -hOption, zum Beispiel du -h | sort -h).

Speichern Sie Folgendes in hr.awk:

BEGIN { split("KMGTPEZY",suff,//)}
{
  match($0,/([0-9]+)[ \t](.*)/,bits)
  sz=bits[1]+0; fn=bits[2]
  i=0; while ((sz>1024)&&(i<length(suff))) { sz/=1024;i++ }
  if (i) printf("%.3f %siB %s\n",sz,suff[i],fn)
  else   printf("%3i B %s\n",sz,fn)
}

Dann können Sie tun:

find $BASE_DIR/ -user $USER -size +$LOWERSIZELIMIT -mtime +$MY_MTIME \
  -type f -printf "%s %p\n" 2> /dev/null | sort -nr |
  gawk -f hr.awk | head -n $NUMFILES >> $TESTFILE

Das Gawk-Skript akzeptiert find ... -printf "%s %p\n"Eingaben und konvertiert das erste Feld in eine für Menschen lesbare Größe mit Suffix (in IEC 2 10- Einheiten).

Siehe auch diese beliebte Frage: https://serverfault.com/questions/62411/how-can-i-sort-du-h-output-by-size

mr.spuratic
quelle