Zählen der Anzahl der Verzeichnisse in einem bestimmten Verzeichnis

103

So zählen Sie die Anzahl der Ordner in einem bestimmten Verzeichnis. Ich verwende den folgenden Befehl, aber er bietet immer einen zusätzlichen.

find /directory/ -maxdepth 1 -type d -print| wc -l

Wenn ich beispielsweise 3 Ordner habe, enthält dieser Befehl 4. Wenn er 5 Ordner enthält, enthält der Befehl 6. Warum ist das so?

user2566898
quelle
4
Die zusätzliche Anzahl von 1 ist aufgrund des aktuellen Verzeichnisses '.' , was auch von 'find' berücksichtigt wird.
Patel Deven

Antworten:

94

find druckt auch das Verzeichnis selbst:

$ find .vim/ -maxdepth 1 -type d
.vim/
.vim/indent
.vim/colors
.vim/doc
.vim/after
.vim/autoload
.vim/compiler
.vim/plugin
.vim/syntax
.vim/ftplugin
.vim/bundle
.vim/ftdetect

Sie können stattdessen die untergeordneten Elemente des Verzeichnisses testen und überhaupt nicht in sie absteigen:

$ find .vim/* -maxdepth 0 -type d
.vim/after
.vim/autoload
.vim/bundle
.vim/colors
.vim/compiler
.vim/doc
.vim/ftdetect
.vim/ftplugin
.vim/indent
.vim/plugin
.vim/syntax

$ find .vim/* -maxdepth 0 -type d | wc -l
11
$ find .vim/ -maxdepth 1 -type d | wc -l
12

Sie können auch verwenden ls:

$ ls -l .vim | grep -c ^d
11


$ ls -l .vim
total 52
drwxrwxr-x  3 anossovp anossovp 4096 Aug 29  2012 after
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 autoload
drwxrwxr-x 13 anossovp anossovp 4096 Aug 29  2012 bundle
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 colors
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 compiler
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 doc
-rw-rw-r--  1 anossovp anossovp   48 Aug 29  2012 filetype.vim
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 ftdetect
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 ftplugin
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 indent
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 plugin
-rw-rw-r--  1 anossovp anossovp 2505 Aug 29  2012 README.rst
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 syntax

$ ls -l .vim | grep ^d
drwxrwxr-x  3 anossovp anossovp 4096 Aug 29  2012 after
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 autoload
drwxrwxr-x 13 anossovp anossovp 4096 Aug 29  2012 bundle
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 colors
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 compiler
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 doc
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 ftdetect
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 ftplugin
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 indent
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 plugin
drwxrwxr-x  2 anossovp anossovp 4096 Aug 29  2012 syntax
Pavel Anossov
quelle
Nett! Wie würden Sie das $ ls -l .vimmit PHP machen? Oder wie man nur die Summe ohne die Liste bekommt. Ich meine, in diesem Fall nur bekommen 52?
Pathros
Hah. Ich finde es toll, wie das Argument gegen PowerShell lautet, dass BASH in jeder Hinsicht einfacher ist. Möchten Sie den POSH-Befehl sehen, um dies zu tun? (ls).Count
Kolob Canyon
@Pathros Verwenden Sie glob mit dem Flag GLOB_ONLYDIR und zählen Sie () das Ergebnis.
Pilipe
1
ls -l | grep -c ^dist ganz einfach und funktioniert. @Pathros gibt es wahrscheinlich einen besseren Weg in PHP, aber im schlimmsten Fall können Sie in PHP immer die Funktion shell_exec () verwenden, um die Befehlszeile auszuführen und Ergebnisse an eine Zeichenfolge zurückzugeben. dh $dirCount = shell_exec('ls -l | grep -c ^d');
Gigabyte
66

Zählen Sie nur die Verzeichnisse im aktuellen Verzeichnis

echo */ | wc

Sie werden wie rauskommen 1 309 4594

2nd digitrepräsentiert nein. von Verzeichnissen.

oder

tree -L 1 | tail -1

EmptyData
quelle
8
Dies schlägt fehl, wenn die Verzeichnisnamen leider Leerzeichen enthalten.
Michael Campbell
zsh: no matches found: */braucht nullglob
Anne van Rossum
@ AnnevanRossum Hast du echo. Typwhich echo
EmptyData
7
Der erste kann noch etwas verbessert werden:echo */ | wc -w
ibic
Nota, dass dies 1 zählt, wenn es keine Verzeichnisse anstelle von 0 gibt.
jinawee
27
find . -mindepth 1 -maxdepth 1 -type d | wc -l

Für find -mindepthbedeutet die Gesamtzahl, die in Verzeichnissen wiederverwendet wird

-maxdepth bedeutet Gesamtzahl in Verzeichnissen

-type d bedeutet Verzeichnis

Und für wc -lMittel zählen die Zeilen der Eingabe

Shiyani Suresh
quelle
2
Können Sie bitte Ihre Antwort erklären (in Ihrer Antwort)?
Zulu
-mindepth bedeutet Gesamtzahl, die in Verzeichnissen wiederverwendet wird, -maxdepth bedeutet Gesamtzahl, die in Verzeichnissen wiederverwendet wird, -type d bedeutet Verzeichnis und wc -l bedeutet Zeilenanzahl aus der angegebenen Verzeichnisliste
shiyani suresh
find . -mindepth 1 -maxdepth 1 -type d | wc -lSie erhalten viele Leerzeichen zwischen den Zahlen, zum Beispiel: `2` Sie können dies verhindern, indem Sie dir_count=`find . -maxdepth 1 -type d | wc -l | xargs`; echo $dir_count # will print just 2 if (( $dir_count > 1 )); then echo "Yaa"; fi # will print "Yaa"
Folgendes
16

Wenn Sie nur Verzeichnisse im Ordner und keine Dateien haben, geschieht dies wie folgt:

ls | wc -l
Brainmaniac
quelle
2
Dies bekommt auch Dateien, aber die Frage war über Ordner / Verzeichnisse.
Robert
12

Beste Weg, um zu Ihrem Laufwerk zu navigieren und einfach auszuführen

ls -lR | grep ^d | wc -l

und um alle Ordner insgesamt zu finden, einschließlich Unterverzeichnisse?

find /mount/point -type d | wc -l

... oder alle Ordner im Stammverzeichnis finden (ohne Unterverzeichnisse)?

find /mount/point -maxdepth 1 -type d | wc -l

Prost!

Manish Shrivastava
quelle
Beachten Sie, dass die vorherigen ls -lRdas Verzeichnis find -type d mit dem Punktpräfix ignorieren, während sie gezählt werden. Daher ist die vom ersten Befehl angegebene Anzahl falsch, wenn Sie Verzeichnisse mit Punktpräfix haben (Beispiel: Sie haben das Unterverzeichnis .git!). Sie können nicht einfach verwenden, -lRada Sie auch für jedes Verzeichnis einen .und einen ..Eintrag erhalten. Dies gilt auch für die Antwort von @Pavel Anossov
Marcz
12

Führen Sie stat -c %h folder2 aus und subtrahieren Sie sie vom Ergebnis. Dies verwendet nur einen einzigen Teilprozess im Gegensatz zu den 2 (oder sogar 3), die von den meisten anderen Lösungen hier benötigt werden (typischerweise findplus wc).

Mit sh / bash:

cnt = $ ((`stat -c% h Ordner` - 2))
echo $ cnt # 'echo' ist ein eingebauter sh / bash-Prozess, kein zusätzlicher Prozess

Verwenden von csh / tcsh:

@ cnt = `stat -c% h Ordner` - 2
echo $ cnt # 'echo' ist ein eingebautes csh / tcsh, kein zusätzlicher Prozess


Erläuterung: stat -c %h folderGibt die Anzahl der Hardlinks zum Ordner aus , und jeder Unterordner unter dem Ordner enthält einen ../-Eintrag, bei dem es sich um einen Hardlink zurück zum Ordner handelt . Sie müssen 2 subtrahieren, da die Anzahl zwei zusätzliche Hardlinks enthält:

  1. Ordner selbstreferenzieller ./ Eintrag, und
  2. Ordner ‚s Eltern Link zu Ordner
textral
quelle
Im Zusammenhang mit dieser Frage: [Warum hat ein neues Verzeichnis eine feste Linkanzahl von 2, bevor etwas hinzugefügt wird? ] ( unix.stackexchange.com/questions/101515 ) Es erklärt, warum dies eine ausgezeichnete Antwort ist. Leider wurde dies nicht genügend beachtet! Es ist zwar eine gute Antwort, aber das Ergebnis hängt leider vom Dateisystem ab, aber für die meisten gängigen Dateisysteme funktioniert dies.
kvantour
8

Ich denke, das ist am einfachsten

  ls -ld images/* | wc -l

Wo imagesist dein Zielverzeichnis? Das Flag -d ist auf Verzeichnisse beschränkt, und das Flag -l führt eine zeilenweise Auflistung durch, die mit der wc -lfür die Zeilenanzahl sehr bekannten Liste kompatibel ist .

Briceburg
quelle
Gibt auch Ergebnis +1
Josef
1
Laut man ls, -dtut: "Verzeichnisse selbst auflisten, nicht deren Inhalt", das heißt, wenn Sie ausführen ls /tmp, erhalten Sie, was drin ist /tmp, und wenn Sie ausführen, erhalten ls -d /tmpSie nur /tmp. Der -dSwitch filtert keine Verzeichnisse, wie gewünscht.
Robert
5

Einige nützliche Beispiele:

Dateien im aktuellen Verzeichnis zählen

/bin/ls -lA  | egrep -c '^-'

Zählverzeichnisse im aktuellen Verzeichnis

/bin/ls -lA  | egrep -c '^d'

Zählen Sie Dateien und Verzeichnisse im aktuellen Verzeichnis

/bin/ls -lA  | egrep -c '^-|^d'

Zählen Sie Dateien und Verzeichnisse in einem Unterverzeichnis

/bin/ls -lA  subdir_name/ | egrep -c '^-|^d'

Ich habe eine seltsame Sache bemerkt (zumindest in meinem Fall):

Wenn ich es lsstattdessen mit /bin/ls dem -AParameter do not list implied . and ..NOT WORK wie erwartet versucht habe. Wenn ich lsdiese Show benutze ./ und ../ Also das Ergebnis falsch zählen. LÖSUNG: /bin/lsstattdessenls

MTK
quelle
4

Kein Verzeichnis, das wir mit dem folgenden Befehl finden können

ls -l | grep "^d" | wc -l

user1388547
quelle
Nur ls -l | grep ^d | wc -lwird es tun, es gibt keine Notwendigkeit, "hier zu verwenden
kaspiotr
3

Eine reine Bash-Lösung:

shopt -s nullglob
dirs=( /path/to/directory/*/ )
echo "There are ${#dirs[@]} (non-hidden) directories"

Wenn Sie auch die versteckten Verzeichnisse zählen möchten:

shopt -s nullglob dotglob
dirs=( /path/to/directory/*/ )
echo "There are ${#dirs[@]} directories (including hidden ones)"

Beachten Sie, dass dies auch Links zu Verzeichnissen zählt. Wenn Sie das nicht wollen, ist es mit dieser Methode etwas schwieriger.


Verwenden von find:

find /path/to/directory -type d \! -name . -prune -exec printf x \; | wc -c

Der Trick besteht darin x, jedes Mal, wenn ein Verzeichnis gefunden wird, ein to stdout auszugeben und dann wcdie Anzahl der Zeichen zu zählen. Dies zählt die Anzahl aller Verzeichnisse (einschließlich versteckter) ohne Links.


Die hier vorgestellten Methoden sind alle sicher für lustige Zeichen, die in Dateinamen (Leerzeichen, Zeilenumbrüche, Glob-Zeichen usw.) vorkommen können.

gniourf_gniourf
quelle
Dies ist die beste Lösung in dieser Frage und wird immer funktionieren!
kvantour
3

Verwenden von zsh:

a=(*(/N)); echo ${#a}

Das Nist ein Nullglob, /macht es mit Verzeichnissen übereinstimmen, #zählt. Leerzeichen in Verzeichnisnamen werden sauber verarbeitet und zurückgegeben, 0wenn keine Verzeichnisse vorhanden sind.

Anne van Rossum
quelle
0

Zählen Sie alle Dateien und Unterordner im Windows-Stil:

dir=/YOUR/PATH;f=$(find $dir -type f | wc -l); d=$(find $dir -mindepth 1 -type d | wc -l); echo "$f Files, $d Folders"
margenn
quelle
0

Wenn Sie reguläre Ausdrücke verwenden möchten, versuchen Sie Folgendes:

ls -c | grep "^d" | wc -l
Makassi
quelle
1
Möchten Sie Ihrer Nur-Code-Antwort eine Erklärung hinzufügen? Es würde helfen, das Missverständnis zu bekämpfen, dass StackOverflow ein kostenloser Dienst zum Schreiben von Code ist. Schauen Sie auch hier, um das Erscheinungsbild zu verbessern: stackoverflow.com/editing-help
Yunnosch
0

Die beste Antwort auf das, was Sie wollen, ist

echo `find . -maxdepth 1 -type d | wc -l`-1 | bc

dies subtrahiert einen, um das unerwünschte '.' zu entfernen. Verzeichnis, das Listen findet (wie oben erwähnt patel deven).

Wenn Sie Unterordner rekursiv zählen möchten, lassen Sie die Option maxdepth einfach weg

echo `find . -type d | wc -l`-1 | bc

PS Wenn Sie die Befehlsersetzung als hässlich empfinden, können Sie sie mit sedund als reinen Stream subtrahieren bc.

Subtrahieren von eins von der Zählung:

find . -maxdepth 1 -type d | wc -l | sed 's/$/-1\n/' | bc

oder Hinzufügen von count zu minus eins:

find . -maxdepth 1 -type d | wc -l | sed 's/^/-1+/' | bc
Dr. Person Person II
quelle
-1

Der beste Weg, es zu tun:

ls -la | grep -v total | wc -l

Dies gibt Ihnen die perfekte Zählung.

Manoj
quelle
6
Du meinst, das ist der schlechtere Weg! Außerdem zählt dies nicht die Anzahl der Verzeichnisse. Und was ist, wenn es einen Verzeichnisnamen gibt, der die Zeichenfolge enthält total? Ihre Methode ist kaputt :(. Nicht analysierenls !
gniourf_gniourf