in reply to Copying files between directories. How can I improve this code.

First off, uncomment use strict;! Then add the my to declare each variable. Note though that you need to declare @Filenames outside the loop.

Note that #recursively search  $path for files is a lie. There is no recursion and the search will only find files in the top level directory. If you want to actually perform a recursive search you need to do a little more work. At that point File::Find is likely what you want. Taking that route, something like the following (untested) code is what you want:

#!/usr/local/bin/perl -W # force taint checks, and print warnings use strict; # install all three strictures use File::Copy; use File::Find; my $path = "sourceDirectory"; #define full path to source folder my $newpath = "destinationDirectory"; #define path to new folder my @Filenames; $|++; # force auto flush of output buffer find (\&doCopy, $path); #Recursively search $path for files to copy sub doCopy { return if ! -f $File::Find::name; chdir($path) || die "cannot move to $path"; my $destFile = $newpath . $_; print "\$destFile = $destFile\n"; copy( "$_" , "$destFile" ) or print "File $_ cannot be copied. $!\ +n"; }

Note that you will probably have to clean up issues regarding paths to destination sub-directories in copy. You will probably need to do some magic with $File::Find::dir to strip off the root path and append the remaining path to $newpath.


DWIM is Perl's answer to Gödel

Replies are listed 'Best First'.
Re^2: Copying files between directories. How can I improve this code.
by richill (Monk) on Apr 22, 2006 at 01:09 UTC
    Thanks, this is what I've got so far,

    At the moment all the source files are found, which is brilliant but they dumped into the destination directory and I'm losing the directory structure.

    Im going to change the code to append the destination varible with the current directory when copy() fails.

    Im going to try the reg ex in the morning.Something like this $\/* to match the / at the end of the string. Then happy days.

    #!/usr/local/bin/perl -W # force taint checks, and print warnings use strict; # install all three strictures use File::Copy; use File::Find; my $path = ""; #define full path to source folder my $newpath = ""; #define path to new folder my @Filenames; #recursively search $path for files opendir (ORIG , $path); @Filenames = readdir ORIG; closedir ORIG; $|++; # force output of buffer find (\&doCopy, $path); #Recursively search $path for files to copy sub doCopy { return if ! -f $File::Find::name; chdir($path) || die "cannot move to $path"; my $destFile = $newpath . $_; #print "\$destFile = $destFile\n"; copy( "$_" , "$destFile" ) or $path = $File::Find::dir ; #print "$_ cannot be copied $!. $File::Find::dir \n" ; }

      Ok, here is a version with a little "magic" done.

      #!/usr/local/bin/perl -W # force taint checks, and print warnings use strict; # install all three strictures use File::Copy; use File::Find; my $path = "C:/Perl/eg"; #define full path to source folder my $newpath = "c:/Delme"; #define path to new folder $| = 1; # force auto flush of output buffer chdir($path) || die "cannot move to $path"; find (\&doCopy, $path); #Recursively search $path for files to copy sub doCopy { return if ! -f $File::Find::name; my $subTree = substr $File::Find::name, 1 + length $path; my $destFile = "$newpath/$subTree"; print "\$destFile = $destFile\n"; #copy ($_, $destFile) or print "File $_ cannot be copied. $!\n"; }

      Prints:

      $destFile = c:/Delme/example.pl $destFile = c:/Delme/Readme.txt $destFile = c:/Delme/aspSamples/ado1.asp $destFile = c:/Delme/aspSamples/ado10.asp $destFile = c:/Delme/aspSamples/ado11.asp $destFile = c:/Delme/aspSamples/ado12.asp $destFile = c:/Delme/aspSamples/ado13.asp $destFile = c:/Delme/aspSamples/ado14.asp $destFile = c:/Delme/aspSamples/ado15.asp ...

      Note that you needn't interpolate variables into strings to pass them as parameters, just pass the variable: copy ($_, $destFile) for example.


      DWIM is Perl's answer to Gödel

        Thats more then I expected, Thankyou.

        my $subTree = substr $File::Find::name, 1 + length $path;

        I see this string declares subtree and initialises it as the name of the file currently in Find. I'm not sure what this does 1 + length $path

        Does it change the value of $path to 1$path for the first folder.

        Actually I know, it uses substr to pullout the part of $File::Find::name after the last /.