For posterity,

Here's another approach that avoids loading the entire list in memory and also neglects the use of -M (it relies specifically on the naming convention of the candidate target files in OP's description).

hauxex points out some caveats using the -M file tests that could render its use unreliable. Gabor Szabo also highlights its weirdness.

Sharing the code below to illustrate the idea behind the computation of the psuedo_mtime field which was used for comparisons.

#!/usr/bin/perl use strict; use warnings FATAL => 'all'; use Getopt::Long qw ( :config no_ignore_case bundling ); use Pod::Usage qw ( pod2usage ); # parse options my (%opt,$dir); GetOptions(\%opt, "help|h", "verbose|v", "test|t", "version", "directo +ry|d=s" => \$dir) || pod2usage(-verbose => 0); pod2usage(-verbose => 1, -exitval => 1) if $opt{'help'}; pod2usage(-verbose => 99, -exitval => 0, -sections => [qw(VERSION)]) i +f $opt{'version'}; pod2usage(-verbose => 0, -message => "$0: No directory given\n") if ! +$dir; my @AGE_RATIONALISER = (31104000,2592000,86400,3600,60,1); # yy,mm,dd, +hh,mm,ss converted to secs my $processed_hash_ref; opendir DH, $dir or die "Couldn't open directory $dir: $!"; chdir $dir; # filetests using relative path while ($_ = readdir (DH)) { next unless -f $_ && m/^\d_\d{4}_\d\d?_\d\d?_\d\d?_\d\d?_\d\d?_table/i; my @old_fname = split /_/; my $new_fname = join ('_', @old_fname[ 7..11 ]); my $psuedo_mtime = 0; # divine a fake but consistent mtime f +rom the filename $psuedo_mtime += $old_fname[$_+1] * $AGE_RATIONALISER[$_] for (0.. +$#AGE_RATIONALISER); # already seen a more recent file with the name we're # planning to use? skip current file next if defined $processed_hash_ref->{$new_fname} && $processed_hash_ref->{$new_fname}->{AGE} > $psuedo_mtime; # file safe to be renamed... for now $processed_hash_ref->{$new_fname}->{OLDNAME} = $_; $processed_hash_ref->{$new_fname}->{AGE} = $psuedo_mtime; } closedir DH; # now proceed to rename items map { print "[!] rename $processed_hash_ref->{$_}->{OLDNAME} to $_\n" if + $opt{'verbose'}; rename $processed_hash_ref->{$_}->{OLDNAME}, $_ unless $opt{'test' +}; } keys %$processed_hash_ref; __END__ =head1 NAME =over 4 rename.pl - file renaming utility =back =head1 SYNOPSIS =over 4 rename.pl [-t | --test] {-d log-file-directory} rename.pl [-v | --verbose] {-d log-file-directory} rename.pl [-h | --help] rename.pl [--version] =back =head1 OPTIONS =over 4 =item B<-t, --test> Test run - no renaming takes place - effectively a simulation =item B<-v, --verbose> Verbose - printout of files to be renamed =item B<-h, --help> Help - prints this manual =back =head1 DESCRIPTION B<This program> will read the given directory and rename a contingent of the files within said directory. Files to be renamed that share the same target name - will have only the most recent one renamed. =head1 AUTHORS Shadowsong =head1 VERSION 0.0.1-beta =cut

In reply to Re: Batch file renaming - on identical name, keep only most recent file, based on dates by shadowsong
in thread Batch file renaming - on identical name, keep only most recent file, based on dates by Anonymous Monk

Title:
Use:  <p> text here (a paragraph) </p>
and:  <code> code here </code>
to format your post, it's "PerlMonks-approved HTML":



  • Posts are HTML formatted. Put <p> </p> tags around your paragraphs. Put <code> </code> tags around your code and data!
  • Titles consisting of a single word are discouraged, and in most cases are disallowed outright.
  • Read Where should I post X? if you're not absolutely sure you're posting in the right place.
  • Please read these before you post! —
  • Posts may use any of the Perl Monks Approved HTML tags:
    a, abbr, b, big, blockquote, br, caption, center, col, colgroup, dd, del, details, div, dl, dt, em, font, h1, h2, h3, h4, h5, h6, hr, i, ins, li, ol, p, pre, readmore, small, span, spoiler, strike, strong, sub, summary, sup, table, tbody, td, tfoot, th, thead, tr, tt, u, ul, wbr
  • You may need to use entities for some characters, as follows. (Exception: Within code tags, you can put the characters literally.)
            For:     Use:
    & &amp;
    < &lt;
    > &gt;
    [ &#91;
    ] &#93;
  • Link using PerlMonks shortcuts! What shortcuts can I use for linking?
  • See Writeup Formatting Tips and other pages linked from there for more info.