Beefy Boxes and Bandwidth Generously Provided by pair Networks
Perl-Sensitive Sunglasses
 
PerlMonks  

Something like File::Find with sorting

by Doctrin (Beadle)
on Feb 16, 2013 at 17:16 UTC ( #1019048=perlquestion: print w/ replies, xml ) Need Help??
Doctrin has asked for the wisdom of the Perl Monks concerning the following question:

Hello dear Monks )) I have simple code with File::Find:
use strict; use File::Find; my $dir = "/some/dir/in/linux"; File::Find::find (\&search, $dir); sub search { if (-f $_) { print "$_\n"; } }
So if I have 1b.xml,1B.xml,67.xml,5a.xml it would give me the following output:
5a.xml 1b.xml 67.xml 1B.xml
How can I do something similar, BUT so that files that have equal lc($_) would be placed next to each other? Like that:
1b.xml 1B.xml 5a.xml 67.xml
or so? Thanks in advance. If my question is not clear - please let me know.

Comment on Something like File::Find with sorting
Select or Download Code
Replies are listed 'Best First'.
Re: Something like File::Find with sorting
by moritz (Cardinal) on Feb 16, 2013 at 17:40 UTC

      Or if you want a per-directory view,

      my @files; sub search { push @files, $_ if -f; } sub handle_directory { @files = sort { lc($a) cmp lc($b) } @files; # do something with @files print "@files\n"; # get ready for the next directory undef @files; } File::Find::find( { wanted => \&search, bydepth => 1, postprocess => \&handle_directory }, $directory );
Re: Something like File::Find with sorting
by Kenosis (Priest) on Feb 16, 2013 at 21:43 UTC

    File::Find::Rule provides a nice front end for File::Find:

    use strict; use warnings; use File::Find::Rule; my $dir = "."; my @files = File::Find::Rule->file()->in($dir); print "$_\n" for sort { lc $a cmp lc $b } @files;

    Partial output:

    .project 10B.xml 10b.xml 1354903584-3827.xlsx 5a.xml 67.xml 6adh.pdb arrays.pl atom.pdb Bio_SeqIO.pl ...

    You may also be interested in using Sort::Naturally for a lexical sort:

    use strict; use warnings; use File::Find::Rule; use Sort::Naturally; my $dir = "."; my @files = File::Find::Rule->file()->in( $dir ); print "$_\n" for nsort @files;

    Partial output

    5a.xml 6adh.pdb 10b.xml 10B.xml 67.xml 1354903584-3827.xlsx arrays.pl atom.pdb Bio_SeqIO.pl Book1.xls
Re: Something like File::Find with sorting
by clueless newbie (Hermit) on Feb 16, 2013 at 18:47 UTC

    Why not use File::Find::find's preprocess option? Something along the lines of

    File::Find::find({preprocess=>sub { return sort {uc $a cmp uc $b} @_ }, wanted=>sub { return if (-d); say $_; } },@ARGV);
Re: Something like File::Find with sorting
by RichardK (Vicar) on Feb 16, 2013 at 17:46 UTC

    Why not put your file names into a list rather than printing them out, and then sorting the list ?

    So, something like this , untested :)

    use strict; use File::Find; my @files; my $dir = "/some/dir/in/linux"; File::Find::find (\&search, $dir); sub search { if (-f $_) { push @files,$_; } } for (sort { your sort criteria here} @files) { say $_; }

    BTW I find it easier to use File::Find::Rule

    my @files = File::Find::Rule->files()->in($dir);

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: perlquestion [id://1019048]
Approved by moritz
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others browsing the Monastery: (7)
As of 2015-07-28 05:53 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    The top three priorities of my open tasks are (in descending order of likelihood to be worked on) ...









    Results (252 votes), past polls