Lance Murray wrote:
> 
> Hello:

Hello,

> I've been away from the Learning Perl book for a few weeks and trying to refresh
> my memory, but I'm stumped.  What I need to do is take the output of a command
> (ovfiltercheck) that looks something like this:
> 
> ### BIN OUTPUT BEGIN #####################
> FilterExpressions {
>   NetBackbone "Networks and gateways/routers"  { (Routers || Networks) }
>   blah, blah,
> }
> 
> Defined Filter List
> ===========
> ATMnodes
> Bridges
> Segments
> 
> Defined Set List
> ================
> FAILOVER_SET
> WHWAN_INFRA_NODES
> ### BIN OUTPUT END ########################
> 
> and get it into an array (i.e @filters) that looks like this:
> ### @filters BEGIN ########################
> ATMnodes
> Bridges
> Segments
> ### @filters END ##########################
> 
> My question is whethor or not its better to parse the data as I load the array
> from the program output, or parse the array after the fact, or parse the array
> after the fact multiple times  In either case I seem to get lost in trying to
> use a foreach and shift at the same time, e.g.:
> 
> #### TRYING TO PARSE PURGE EVERYTHING TO "Defined Filter List" +two elements)
> my @filters = `/opt/OV/bin/ovfiltercheck`;
> foreach ( @filters ) {
>   if ( m/Defined Filter List/ ) { # IF FIND FILTER SECTION
>     shift;   # DELETE "Defined Filter List"

shift with no arguments removes elements from the array @ARGV in the
main program or from the array @_ in a subroutine so it is having no
effect on the array @filters.  But you shouldn't modify an array in a
foreach loop anyways.


>     shift;   # DELETE "================"
>     last;    # EXIT FOREACH LOOP
>   } else {
>     shift;   # DELETE ELEMENTS
>   }
> }
> # Make another foreach loop to dump elements after "Defined Set List"
> print @filters;
> 
> In my mind, I'm thinking from DB perspective where I'm deleting the current
> record, not just the element at the start (shift) or end of an array (push).  Is
> there any way to dump an element anywhere? (e.g., pop $array[$anyElement] or
> shift $anyElement[5])
> 
> ### ANOTHER PATHETIC ATTEMPT
> my ( @filters, $filters_begin, $filters_end) ;
> open OVFILTERCHECK, "/opt/OV/bin/ovfiltercheck |" || die "Error, can't open: $!\n";
                                                    ^^
The '||' operator's precedence is too high for this to work properly. 
You need to use the low precedence 'or' operator or use parenthesis to
set the correct precedence.


> while (<OVFILTERCHECK>) {
>     if ( m/Defined Filter List/ ) { # WHEN I GET TO THE FILTER LIST
>       $filters_begin = 1;           # SET A FLAG INDICATING SAME
>     }
>     if ( m/Defined Set List/ ) {    # WHEN PASS THE FILTER  SECTION
>       last;                         # TERMINATE ARRAY LOADING
>     }
>     if ($filters_found) {           # IF FILTER SECTION HAS BEGUN
>       $filters[$.++]  = $_;         # SAVE VALID FILTER NAMES TO @FILTERS
>  }
> print @filters;
> 
> Sorry for the crappy psuedocode that shows I don't have a clue.  Its been a long
> day and my brain feels like its fried.  All I want to do is "cut" (save to an
> array) the text between the words "Defined Filter List\n================" and
> "\nDefined Set List".  Any help would be appreciated and a true solution worth a
> Six Dollar burger & movie via PayPal (in other words, I'll pay out of pocket).

Here is one way to do it:

my ($output) = `/opt/OV/bin/ovfiltercheck` =~ /^Defined Filter
List\n=+\n(.+?)\n\n/ms;
my @filters = split /\n/, $output;
print @filters;


Another way to do it:

my $prog = '/opt/OV/bin/ovfiltercheck';
open PIPE, "$prog |" or die "Cannot open pipe to $prog: $!";

my @filters;
while ( <PIPE> ) {
    next if 1 .. /^Defined Filter List/;
    last if /^\s*$/;
    chomp;
    push @filters, $_ unless /^=+$/;
    }

close PIPE or die "Cannot close pipe to $prog: $!";
print @filters;




John
-- 
use Perl;
program
fulfillment

-- 
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Reply via email to