Beefy Boxes and Bandwidth Generously Provided by pair Networks
Your skill will accomplish
what the force of many cannot

regexp problem using custom markup

by kidd (Curate)
on Jul 25, 2002 at 20:30 UTC ( #185327=perlquestion: print w/replies, xml ) Need Help??
kidd has asked for the wisdom of the Perl Monks concerning the following question:

I have this problem that has been driving me nuts, and I can't find the answer...

Lets say I have this code:

my $text = 'This test creates a [color=blue] blue [/color] word. And a + [color=red] red [/color] one';
As you can see its a string with special command [color=blue] wich I want to substitute for "<font color="blue">" and [/color] to "</font>"...

Now here is the code I've been trying out:

my ($color,@colors); my $new = $text; @colors = $new =~ m/\[color=.*\]/gi; print @colors;
Now...according to me "@colors" should print out:

[color=blue] [color=red]

Wich it isnt happening...could someone help me out... THANKS

Replies are listed 'Best First'.
Re: Regexp
by dws (Chancellor) on Jul 25, 2002 at 20:40 UTC
    Try @colors = $new =~ m/(\[color=.*?\])/gi;
    Adding the '?' makes the regex non-greedy. When it's greedy, it will merrily swallow everying until it reaches the last ']' in the target string.

Re: Regexp
by thelenm (Vicar) on Jul 25, 2002 at 20:42 UTC
    What you're probably seeing is the greedy behavior of dot-star. .* will match as much as it possibly can, so in your example, it should match "blue] blue [/color] word. And a [color=red] red [/color", not "blue". You could change your regular expression to one of the following options:
    # non-greedy dot-star @colors = $new =~ m/(\[color=.*?\])/gi; # say what you mean: match non-] characters @colors = $new =~ m/(\[color=[^\]]*\])/gi;

    -- Mike


Re: Regexp
by elusion (Curate) on Jul 25, 2002 at 20:42 UTC
    This code should work: @colors = $new =~ m/(\[color=.*?\])/gi;

    First off, @colors will receive values that are kept by parentheses, and you don't have any in your regex.

    And second, the .* in your regex will make it match "[color=blue] blue [/color] word. And a [color=red] red [/color]" all at once because regexes are greedy -- they match as much as possible. By adding the ? behind .* it matches as little as possible.

    elusion :

Re: Regexp
by mkmcconn (Chaplain) on Jul 25, 2002 at 20:40 UTC
      If there are no parentheses, it returns a list of all the matched strings, as if there were parentheses around the whole pattern. -- perlop / Regexp Quote-Like Operators


        Thank you Anomo - you are right. Without the /g operator it will return '1'; but, it will capture just fine using the operator: something that frankly I have never used or noticed.
        Thanks again.

Re: Regexp
by kidd (Curate) on Jul 25, 2002 at 20:45 UTC
    Thanks for your answers...I added the ? and it worked great...
OT: Deprecated Element
by BorgCopyeditor (Friar) on Jul 25, 2002 at 21:55 UTC

    Not what you were asking for, but maybe informative anyway: <font> has been deprecated. Inline styles (or classes) via CSS are preferred, in order to better separate content data (HTML markup) from presentation data (styling).

    --Your punctuation skills are insufficient!

Log In?

What's my password?
Create A New User
Node Status?
node history
Node Type: perlquestion [id://185327]
Approved by osfameron
and all is quiet...

How do I use this? | Other CB clients
Other Users?
Others avoiding work at the Monastery: (10)
As of 2017-03-24 13:05 GMT
Find Nodes?
    Voting Booth?
    Should Pluto Get Its Planethood Back?

    Results (301 votes). Check out past polls.