Rory has asked for the wisdom of the Perl Monks concerning the following question:

I'm new to this forum.

This is my first post!

I have an issue what I am trying to get a list of filenames and filter out some filenames.

For instance in a subdirectory "temp" I have the following file names:

hello.pl hTllo.pl hVllo.pl hQllo.pl

I want to retrieve a list of file names but not include filenames with the second character of 'T' or 'V'.

In other words I want the file names:

hello.pl hQllo.pl

The code I've written is:

######################################################## #!/usr/bin/perl -w my @{Files}; my ${FileName} = "h[[^TV]]*.pl"; my ${f} = ""; @Files = <temp\${FileName}>; printf ("\n##############[ ${FileName} ]####################\n"); foreach ${f} (@Files) { printf("${f}\n"); } printf ("##################################\n"); ########################################################

The response I get is:

##############[ h[[^TV]]*.pl ]#################### temp\hTello.pl temp\hVello.pl ##################################

The references tell me the '^' character is a NOT and should filter out the T and V characters... but does not.

Any suggestions?

20070320 Janitored by Corion: Added formatting, code tags, as per Writeup Formatting Tips

Replies are listed 'Best First'.
Re: File name filtering with ^ ?
by cdarke (Prior) on Mar 19, 2007 at 22:14 UTC
    I can understand your confusion. Filename wilcards, or glob constructs, use a simpler and DIFFERENT set of meta-characters from Regular Expressions (REs). In REs ^ means 'not' inside [...], but in globbing we use !, so you need [!TV].
    You might also like to consider using the glob function instead of <>, particularly when using patterns from variables. <> are also used for reading files, and the code can get confusing. If you have filenamess with embedded spaces also look at module File::Glob. Update: corrected typos
Re: File name filtering with ^ ?
by Anno (Deacon) on Mar 19, 2007 at 22:10 UTC
    You're using regeular expression syntax in a glob. While character classes work in globs much like they do in regular expressions, the negation trhrough "^" is not supported.

    Anno

Re: File name filtering with ^ ?
by Bro. Doug (Monk) on Mar 19, 2007 at 22:19 UTC
    Rory.

    Thanks for posting :)

    ^ signifies the beginning unless you're inside of square brackets, in which case (as cdarke pointed out) it means 'not'.

    What you're probably looking for is something like:
    my @files = () ; opendir DIR, '/path/to/dir' ; foreach( readdir DIR ){ # do this unless it matches a digit or char followed by T # or V followed by anything. push @files, $_ unless/[\d\w][TV].*/ ; }
    Bro. Doug :wq
      [\d\w] is the same as \w, and adding an anchor to the regex pattern might be more efficient:
      
         push @files, $_ if /^\w[^TV]/; 
      
      or simply:
      
         my @files = grep {/^\w[^TV]/} glob("*.pl");
      
      or try shell to negate the character-class:
      
         my @files = glob("h[!TV]*.pl");
      
      Regards, 
      Xicheng