39 Stimmen

Wie lese ich den Inhalt eines Verzeichnisses in Perl ein?

Wie bringe ich Perl dazu, den Inhalt eines bestimmten Verzeichnisses in ein Array einzulesen?

Backticks kann dies tun, aber gibt es eine Methode, die "scandir" oder einen ähnlichen Begriff verwendet?

58voto

jj33 Punkte 7234
opendir(D, "/path/to/directory") || die "Can't open directory: $!\n";
while (my $f = readdir(D)) {
    print "\$f = $f\n";
}
closedir(D);

EDIT: Oh, sorry, ich habe den Teil "in ein Array" übersehen:

my $d = shift;

opendir(D, "$d") || die "Can't open directory $d: $!\n";
my @list = readdir(D);
closedir(D);

foreach my $f (@list) {
    print "\$f = $f\n";
}

EDIT2: Die meisten anderen Antworten sind zutreffend, aber ich wollte auf Folgendes hinweisen diese Antwort in dem diese Lösung angeboten wird:

opendir(DIR, $somedir) || die "Can't open directory $somedir: $!";
@dots = grep { (!/^\./) && -f "$somedir/$_" } readdir(DIR);
closedir DIR;

Erstens, um zu dokumentieren, was es tut, da der Poster es nicht getan hat: Es übergibt die zurückgegebene Liste von readdir() durch eine grep() die nur die Werte zurückgibt, bei denen es sich um Dateien handelt (im Gegensatz zu Verzeichnissen, Geräten, benannten Leitungen usw.) und die nicht mit einem Punkt beginnen (wodurch der Name der Liste @dots irreführend, aber das liegt an der Änderung, die er beim Kopieren von der readdir()-Dokumentation vorgenommen hat). Da es den Inhalt des zurückgegebenen Verzeichnisses einschränkt, glaube ich nicht, dass es technisch gesehen eine korrekte Antwort auf diese Frage ist, aber es veranschaulicht eine übliche Redewendung, die zum Filtern von Dateinamen in Perl und ich dachte, es wäre gut, das zu dokumentieren. Ein anderes Beispiel, das man oft sieht, ist:

@list = grep !/^\.\.?$/, readdir(D);

Dieses Snippet liest alle Inhalte aus dem Verzeichnis-Handle D außer '.' und '..', da diese sehr selten in der Auflistung verwendet werden sollen.

19voto

Pat Punkte 35602

Eine schnelle und schmutzige Lösung ist die Verwendung von Globus

@files = glob ('/path/to/dir/*');

9voto

rix0rrr Punkte 9278

So geht's, in einer Zeile (beachten Sie den Platzhalter '*' am Ende)

@files = </path/to/directory/*>;
# To demonstrate:
print join(", ", @files);

9voto

Gary Richardson Punkte 15543

IO::Dir ist schön und bietet auch eine gebundene Hash-Schnittstelle.

Aus der Perldoc:

use IO::Dir;
$d = IO::Dir->new(".");
if (defined $d) {
    while (defined($_ = $d->read)) { something($_); }
    $d->rewind;
    while (defined($_ = $d->read)) { something_else($_); }
    undef $d;
}

tie %dir, 'IO::Dir', ".";
foreach (keys %dir) {
    print $_, " " , $dir{$_}->size,"\n";
}

Sie könnten also etwas tun wie:

tie %dir, 'IO::Dir', $directory_name;
my @dirs = keys %dir;

5voto

David Precious Punkte 6455

Sie könnten verwenden DirHandle :

use DirHandle;
$d = new DirHandle ".";
if (defined $d)
{
    while (defined($_ = $d->read)) { something($_); }
    $d->rewind;
    while (defined($_ = $d->read)) { something_else($_); }
    undef $d;
}

DirHandle bietet eine alternative, sauberere Schnittstelle zum opendir() , closedir() , readdir() y rewinddir() Funktionen.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X