Perl : Delete all files except few

I have a directory like below. Need help with Perl to delete all files under test1 except the one passed as parameters.The parameters will
always be the directories under test1 in the format below.

EX:

dir1/abc.txt,dir2/test.xml,dir3/dfb.txt,dir4/text.xml
test1  
            ---dir1
                  abc.txt
                  def.txt
                  test.xml
                  test.csv
                  test.xml
            ---dir2
                  fgh.txt
                  jhk.txt
                  test.xml
                  test.csv
                  test.xml                   
            ---dir3
                  rth.txt
                  dfb.txt
                  test.xml
                  test.csv
                  test.xml
            ---dir4 
                  ert.txt
                  def.txt
                  test.xml
                  test.csv
                  test.xml

Did not find negation for unlink in perl.:frowning:

Have a look at the File::Find module.
You could store the arguments passed in a hash and then test the files/directories found.
Be a bit careful though...
Good luck.

New to perl :frowning: Not familiar with hashes

Put this into "script.pl":

#!/usr/bin/perl
use strict;
use warnings;
use Getopt::Std;
use File::Find;

our ($opt_d, $opt_e);
getopt("de");
die "exclude is not defined (no parameter for -e)" unless defined $opt_e;
our $dir = $opt_d;
die "$dir is not a directory (wrong parameter for -d)" unless -d $dir;
our @exclude = split /,/, $opt_e;

finddepth(\&wanted, "$dir");

sub wanted {
  if (( ! grep {$File::Find::name eq "$dir/$_"} @exclude) && (-f $_)) {
    unlink $_;
  }
}

Then run the script as:

./script.pl -d/path/to/test1 -e"dir1/abc.txt,dir2/test.xml,dir3/dfb.txt,dir4/text.xml"
1 Like

@bartus11: Thanks a lot it works great...!!!:b: One last question how to include a echo statement if any one of the files passed as parameters are not present in the directory.

Try:

#!/usr/bin/perl
use strict;
use warnings;
use Getopt::Std;
use File::Find;

our ($opt_d, $opt_e);
getopt("de");
die "exclude is not defined (no parameter for -e)" unless defined $opt_e;
our $dir = $opt_d;
die "$dir is not a directory (wrong parameter for -d)" unless -d $dir;
our @exclude = split /,/, $opt_e;

foreach my $file (@exclude) {
  print "$dir/$file not found\n" if ! -f "$dir/$file";
}

finddepth(\&wanted, "$dir");

sub wanted {
  if (( ! grep {$File::Find::name eq "$dir/$_"} @exclude) && (-f $_)) {
    unlink $_;
  }
}