ok i have a perl script

use strict;
use warnings;

open(my $in, ">>", "log.txt") or die "cant open log.txt $!" ;

my @files = <*>;
foreach my $file (@files){
print $in $file . "\n";
}

close $in or die "$in $!";

it gets the filenames that are in the same dir as script.

but if there is an other dir in there it needs to look in there and list those files to.

like

bla.txt
blabla.txt
bla/bla3.txt
ect

#!/usr/bin/perl
#print_files_in_subdirs.pl
use strict;
use warnings;
my $startdir = '/home/david/Programming/data';
print_files($startdir);

sub print_files {
    #This subroutine calls itself for each subdirectory it finds.
    my $dir = $_[0];
    my @files = <$dir/*>;
    my @d;
    foreach (@files) {
        next if $_ eq "." or $_ eq "..";
        my $fn = $_;
        if (-d $fn) {
            push @d, $fn;
        }
        else{
            print "$fn\n";
        }
    }
    if (scalar @d == 0) { #If no directories found, $dir is lowest dir in this branch
        return;
    }
    foreach (@d) {
        print_files($_);
    }
}
Comments
Works for me.

The default iterator variable in a foreach loop if no other variable is supplied.

from perldoc perlvar.

If we supply another variable, such as $fn, in the loop condition then we won't need $_. I just used it out of habit. The foreach loop can work just as well as follows.

foreach my $fn (@files) {
        next if $fn eq "." or $fn eq "..";
        
        if (-d $fn) {
            push @d, $fn;
        }
        else{
            print "$fn\n";
        }
    }
This article has been dead for over six months. Start a new discussion instead.