Beefy Boxes and Bandwidth Generously Provided by pair Networks
more useful options
 
PerlMonks  

matching pattern question?

by BhariD (Sexton)
on Jun 07, 2011 at 15:56 UTC ( [id://908515]=perlquestion: print w/replies, xml ) Need Help??

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

if I have a string with possible following patterns, could be other combinations of 0's and 1's, longer in length, this is just an example.

my @string = ('0110','1','11','01110','001','100','1111','01001110');

I want only the patterns that has more than 2 consecutive 1's in the string, no all 0's, no "010110" cases. The output for above should be:

01110 111

I use the following match expression, not completely doing what I want

foreach my $string (@string){ if(($string =~ m/1(?=[^1])/g)||($string =~ m/^0+$/g)){ print "not a match\n"; } else{print $string, "\n";} }

any suggestions?,

Replies are listed 'Best First'.
Re: matching pattern question?
by Corion (Patriarch) on Jun 07, 2011 at 16:10 UTC

    Maybe it helps if you think about your question in another way?

    It sounds to me as if you want to match all strings that start with a sequence of zeroes (or possibly none at all), then the string "11", then possibly some more ones, and then possibly zeroes. This should be easily writeable as a regular expression requiring no special features beyond *.

Re: matching pattern question?
by ChrisDennis (Sexton) on Jun 07, 2011 at 16:36 UTC

    Can't you just do this?

    if($string =~ m/111/){

    or have I misunderstood the question?

    cheers, Chris

Re: matching pattern question?
by zek152 (Pilgrim) on Jun 07, 2011 at 16:08 UTC

    I do not understand your specification. You state that I want only the patterns that has more than 2 consecutive 1's in the string, no all 0's, no "010110" cases.

    Please elaborate what you mean by "no all 0's" (a string that has more than 2 consecutive 1's can not have all 0's). Also what do you mean by "no '010110' cases"? ("010110" does not have more than 2 consecutive 1's).

    You say that the output should be "01110","111". I assume you meant that "111" should be "1111" since "111" is not in the array.

    Also please explain why "01001110" should not match. It contains 3 consecutive 1's.

    The following regular expression works for your listed requirements (although I suspect that the requirements are not exhaustive).

    if($string =~ /([01]*111[01]*)/){ print "$string\n" } #output #01110 #1111 #01001110

      I, also, do not understand the OP, but zeroing in on the "I want only the patterns that has more than 2 consecutive 1's ..." portion as zek152 has, I would code the regex slightly differently (I don't understand the  [01]* bits):

      >perl -wMstrict -le "my @strings = qw(0110 1 11 01110 001 100 1111 01001110); my @three_or_more = grep { m{ 1{3} }xms } @strings; printf qq{'$_' } for @three_or_more; " '01110' '1111' '01001110'
Re: matching pattern question?
by ww (Archbishop) on Jun 07, 2011 at 19:28 UTC
    Perhaps OP means to capture the entire data string when that string contains three or more consecutive "1"s?

    If so, in additional to AnomalousMonk's grep suggestion, several of the others above are solutions or near solutions with the addition of capturing parens:

    #!/usr/bin/perl use strict; use warnings; use 5.012; my @captures; my $capture; my $string; my @strings = qw/0110 1 11 01110 001 100 1111 01001110/; for $string(@strings) { if ( $string =~ /^(.*?1{3}.*)$/ ) { push @captures, $1; } } for $capture(@captures) { say $capture; }

    which produces:

    01110 1111 01001110
Re: matching pattern question?
by AR (Friar) on Jun 07, 2011 at 16:52 UTC

    I think what you want is /^0*1{3,}0*$/.

    Second Edit: After having re-read the question several times, I think what you might want is /^(0|1{3,})*1{3,}(0|1{3,})*$/

Re: matching pattern question?
by BhariD (Sexton) on Jun 07, 2011 at 19:44 UTC

    Sorry, for the confusion. What I mean is- a string could have several different possible combinations of "0" and "1" of different lengths. Out of all possibilities, I need to extract strings with more than 2 consecutive 1's, irrespective of whether they have 0's in start (eg., 0111) or end (e.g., 1110) or both (e.g., 01110, 00111100) or no 0's at all (eg., 111). In sporadic cases such as 00111011' or 0111001111 have more than 2 consecutive 1's, but also has 1's separated by 0's in other locations, however as it qualifies the condition it should be output

      I'm pretty sure I got it above with /^(0|1{3,})*1{3,}(0|1{3,})*$/. Does that work as you expect?

Log In?
Username:
Password:

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

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

    No recent polls found