Beefy Boxes and Bandwidth Generously Provided by pair Networks
No such thing as a small change
 
PerlMonks  

"Deep recursion" error

by cspctec (Sexton)
on Jun 28, 2013 at 16:08 UTC ( [id://1041281]=perlquestion: print w/replies, xml ) Need Help??

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

I am trying to write a script that will run through a directory, check if something is a file and print the filename, and if it is a directory, descend into the directory and print all files filenames, then go back up a directory and finish printing the files in the starting directory. A recursive script. This is my code:
#!/usr/bin/perl -w use strict; my $dir = `pwd`; sub start { foreach (<$dir*>) { print "$_\n" if (-f $_); if (-d $_) { $dir = $_; &start; } } } &start;
When I run this, I'm getting the message "Deep recursion on subroutine "main::start" at ./archive.pl at line 14". I know I'm doing something wrong, but I can't figure out what it is. I guess I am missing a "base case" to make the loop stop, but I don't know how to add a base case in this situation.

Also, this is just a personal project. I don't want to use other perl modules to make it easier. I want to look at each file individually.

Replies are listed 'Best First'.
Re: "Deep recursion" error
by BrowserUk (Patriarch) on Jun 28, 2013 at 16:15 UTC

    The first value returned by the glob <somedir*> will be '.'; and the first value returned by <.*> while be '.'; and the first value ...


    With the rise and rise of 'Social' network sites: 'Computers are making people easier to use everyday'
    Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
    "Science is about questioning the status quo. Questioning authority".
    In the absence of evidence, opinion is indistinguishable from prejudice.
Re: "Deep recursion" error
by sundialsvc4 (Abbot) on Jun 28, 2013 at 16:28 UTC

    Even if you don’t choose to use a File::Find type module, you certainly can use their core techniques ... which don’t involve recursion.   Instead, they use a simple push-down stack.

    You start by pushing the starting location on the stack.   Then, something like this:

    while (the stack is not empty) { pop a name off the stack search that directory for entries: -- if it is "." or ".." then SKIP it. (Guess this is what you're +not doing.) -- if it is a directory, "push" or "unshift" the fully-qualified n +ame onto the stack. -- if it is a file, process it, or stack it on another queue it to + be processed soon. }

    If you push the names, you get a “depth-first” search; if you unshift them, “breadth-first.”

    This also circumvents another file-system bugaboo, especially noticeable in Windows:   the number of active “searches” that you can actually have going at one time, and the problem of interference between them.   Only one search is actually going-on at one time.

Re: "Deep recursion" error
by Laurent_R (Canon) on Jun 28, 2013 at 17:55 UTC

    The deep recursion message is not necessarily an error, it is a warning telling you that you have stacked more than 100 calls. But in this case, it tells you something useful, because you actially have an error.

    In general, if you want to recurse, you need to pass at least one parameter to the function that is called recursively, so that it can work on a local copy of that parameter. Here, you don't pass any parameter to your start function. BTW the &start syntax is deprecated, use rather start() or start(list of params).

Re: "Deep recursion" error
by RichardK (Parson) on Jun 28, 2013 at 18:07 UTC

    Try single stepping through your program with the perl debugger perldebug / debugging tutorial and maybe you'll see why it's not working.

Re: "Deep recursion" error
by cspctec (Sexton) on Jun 28, 2013 at 17:53 UTC
    Thanks for the suggestions guys. The file globbing thing I was doing doesn't seem to be working out. I feel like I'm close, but I just can't get the script to descend into directories. I really wanted to use recursion to do this, for practice mainly.

    I started over using opendir and readdir. Maybe file globbing just doesn't work properly with recursion, or maybe its just me.

      Yes, you are close ..

      #!perl use strict; use Cwd; # pwd has line ending, use this my $dir = cwd(); # protect against endless loop just in case ! my $limit = 10_000; # call with parameter start($dir); sub start { my $dir = shift; # add / to descend foreach (<$dir/*>) { die "exceeded limit" if --$limit < 0; print " $_ is file\n" if (-f $_); if (-d $_) { print "$_ is a dir\n"; start($_) } } }
      poj
        Thank you poj, that works perfectly.

Log In?
Username:
Password:

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

How do I use this?Last hourOther CB clients
Other Users?
Others chanting in the Monastery: (4)
As of 2024-04-19 03:32 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found