Ask a Question related to PERL Beginners, Design and Development.

  1. #1

    Default breaking the loop

    Howdy:

    I'm trying to find the best solution for breaking
    out of a loop when editing a list of files.

    I have a script that:

    * gets a list of files
    * opens the files with a 'foreach $f(@list)'
    * does a 'while <> { ... } close (FILE)'

    The script works, but if I run it, it loops
    continually and edits (then re-edits) the files.
    I think I could use a lock file to do until I
    get a particular file, but I'm not sure how
    to go about it - at the same time, it may not be
    the more productive way to go.

    [--snip script--]
    my @list = grep {/\.txt/ } readdir(DIR) or die "Can not read the dir\n";

    # create a loop to search for instances of
    # control characters and change it to something else


    foreach $file(@list) {
    open (FILE, $file) or die "can not open this file: $!";

    local $^I=".bak"; # to keep a backup of the files
    # set to "" if i don't want backups
    local @ARGV = @list; # the files to work on
    while (<>) {
    s!$pattern!$new_ptrn!g ;
    print;
    } # end while loop
    close (FILE);
    } #end of for loop


    close (DIR);

    __END__
    [/--snip script--]

    Any suggestions? Thanks!

    -X

    Shaunn Johnson Guest

  2. Similar Questions and Discussions

    1. Loop option set, but flash doesn't loop
      I'm loading some swf files on my website and they all use the same code. They include the loop=true command but some loop and some don't. Does...
    2. Can a film loop play once, then loop on the last frame(s)?
      I need a film loop to play once, then loop playback on the last frame so I can keep the LOOP of the film loop set. This will allow the tell commands...
    3. Film loop rollovers working with tell sprite, but only if Loop is checked
      on mouseWithin me cursor 280 tell sprite 40 --the sprite containing the film loop sprite(60).member = member("networkmapsbuttonroll") --swapping...
    4. Urgent: Repeat loop and Film loop clash!
      Hi All, Scenario I have a script running in which the spelling which was typed in by the student is corrected. The alphabets are moved to...
    5. Help with loop inside loop and mysql queries
      Hi List. I cannot see my error: I have relation tables setup. main id entity_name main_type etc etc date_in 1 test type1 x y 2003-06-02...
  3. #2

    Default RE: breaking the loop

    Perldoc -f last
    Perldoc -f next

    -----Original Message-----
    From: Johnson, Shaunn [mailto:SJohnson6@bcbsm.com]
    Sent: Tuesday, September 16, 2003 4:22 PM
    To: perl beginners
    Subject: breaking the loop


    Howdy:

    I'm trying to find the best solution for breaking
    out of a loop when editing a list of files.

    I have a script that:

    * gets a list of files
    * opens the files with a 'foreach $f(@list)'
    * does a 'while <> { ... } close (FILE)'

    The script works, but if I run it, it loops
    continually and edits (then re-edits) the files.
    I think I could use a lock file to do until I
    get a particular file, but I'm not sure how
    to go about it - at the same time, it may not be
    the more productive way to go.

    [--snip script--]
    my @list = grep {/\.txt/ } readdir(DIR) or die "Can not read the dir\n";

    # create a loop to search for instances of
    # control characters and change it to something else


    foreach $file(@list) {
    open (FILE, $file) or die "can not open this file: $!";

    local $^I=".bak"; # to keep a backup of the files
    # set to "" if i don't want backups
    local @ARGV = @list; # the files to work on
    while (<>) {
    s!$pattern!$new_ptrn!g ;
    print;
    } # end while loop
    close (FILE);
    } #end of for loop


    close (DIR);

    __END__
    [/--snip script--]

    Any suggestions? Thanks!

    -X

    Paul Kraus Guest

  4. #3

    Default Re: breaking the loop

    On Sep 16, Johnson, Shaunn said:
    >* gets a list of files
    >* opens the files with a 'foreach $f(@list)'
    >* does a 'while <> { ... } close (FILE)'
    >
    >The script works, but if I run it, it loops
    >continually and edits (then re-edits) the files.
    >I think I could use a lock file to do until I
    >get a particular file, but I'm not sure how
    >to go about it - at the same time, it may not be
    >the more productive way to go.
    Your code is doing too much work.
    >my @list = grep {/\.txt/ } readdir(DIR) or die "Can not read the dir\n";
    This creates the list of files.
    >foreach $file(@list) {
    >open (FILE, $file) or die "can not open this file: $!";
    >
    >local $^I=".bak"; # to keep a backup of the files
    > # set to "" if i don't want backups
    >local @ARGV = @list; # the files to work on
    Perhaps you mean

    local @ARGV = $file;

    instead.
    > while (<>) {
    > s!$pattern!$new_ptrn!g ;
    > print;
    > } # end while loop
    > close (FILE);
    >} #end of for loop
    Better yet, remove the for loop. I'll show the code in a moment.
    >close (DIR);
    That should be closedir().

    You can do this without opendir(), and without grep() or the for loop.

    {
    local $^I = ".bak";
    local @ARGV = glob "$directory/*.txt";
    while (<>) {
    s/foo/bar/g;
    print;
    }
    }

    Ta da!

    --
    Jeff "japhy" Pinyan [email]japhy@pobox.com[/email] [url]http://www.pobox.com/~japhy/[/url]
    RPI Acacia brother #734 [url]http://www.perlmonks.org/[/url] [url]http://www.cpan.org/[/url]
    <stu> what does y/// stand for? <tenderpuss> why, yansliterate of course.
    [ I'm looking for programming work. If you like my work, let me know. ]

    Jeff 'Japhy' Pinyan Guest

  5. #4

    Default Re: breaking the loop

    Shaunn Johnson wrote:
    >
    > Howdy:
    Hello,
    > I'm trying to find the best solution for breaking
    > out of a loop when editing a list of files.
    >
    > I have a script that:
    >
    > * gets a list of files
    > * opens the files with a 'foreach $f(@list)'
    > * does a 'while <> { ... } close (FILE)'
    >
    > The script works, but if I run it, it loops
    > continually and edits (then re-edits) the files.
    > I think I could use a lock file to do until I
    > get a particular file, but I'm not sure how
    > to go about it - at the same time, it may not be
    > the more productive way to go.
    >
    > [--snip script--]
    > my @list = grep {/\.txt/ } readdir(DIR) or die "Can not read the dir\n";
    >
    > # create a loop to search for instances of
    > # control characters and change it to something else
    >
    > foreach $file(@list) {
    > open (FILE, $file) or die "can not open this file: $!";
    >
    > local $^I=".bak"; # to keep a backup of the files
    > # set to "" if i don't want backups
    > local @ARGV = @list; # the files to work on
    > while (<>) {
    You are looping through all the files in @list using foreach above and
    then you are looping through all the files in @list using while (<>).
    This means that you are modifying each file the number of times for each
    file in the directory. Are you sure this even works at all because you
    are not prepending the directory name to the file name?

    > s!$pattern!$new_ptrn!g ;
    > print;
    > } # end while loop
    > close (FILE);
    > } #end of for loop
    >
    > close (DIR);
    >
    > __END__

    Something like this should work:

    my $dir = '/home/someone';
    local $^I = '.bak'; # to keep a backup of the files
    # set to "" if i don't want backups

    opendir DIR, $dir or die "Cannot open $dir: $!";
    local @ARGV = map "$dir/$_", grep /\.txt$/, readdir DIR;
    close DIR;

    # create a loop to search for instances of
    # control characters and change it to something else

    while ( <> ) {
    s!$pattern!$new_ptrn!g;
    print;
    } # end while loop

    __END__



    John
    --
    use Perl;
    program
    fulfillment
    John W. Krahn Guest

  6. #5

    Default Re: breaking the loop

    Jeff 'japhy' Pinyan wrote:
    > You can do this without opendir(), and without grep() or the for loop.
    >
    > {
    > local $^I = ".bak";
    > local @ARGV = glob "$directory/*.txt";
    > while (<>) {
    > s/foo/bar/g;
    > print;
    > }
    > }
    >
    > Ta da!
    >
    Score one for Japhy!

    This is the first time I have seen the diamond or in-place editing operator
    used well. Usually I blanch when I see them--the diamond conjures up the
    image of some poor shmuck typing in lists of filenames at the command-line,
    and the in-place suggests a delusory "economy" where there really is none in
    the processing itself.. Here, with the encapsulation within a small block,
    the immediacy of the assignment of @ARGV relative to its use in feeding the
    diamond, and the overall brevity of the code, it makes good sense and makes
    the process more clear by abstracting the [in this case] irrelevant details of
    file access.

    Thanks,

    Joseph

    R. Joseph Newton Guest

  7. #6

    Default Re: breaking the loop

    On Saturday, September 27, 2003, at 01:57 PM, R. Joseph Newton wrote:
    > This is the first time I have seen the diamond or in-place editing
    > operator
    > used well. Usually I blanch when I see them--the diamond conjures up
    > the
    > image of some poor shmuck typing in lists of filenames at the
    > command-line...
    This seems a strange thing to say, to me. The diamond operator is
    simple a shortcut to implementing the UNIX filter methodology, which I
    believe has done quite well proving it's usefulness over the years.

    James

    James Edward Gray II Guest

Posting Permissions

  • You may not post new threads
  • You may post replies
  • You may not post attachments
  • You may not edit your posts

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139