简体   繁体   中英

Reluctant quatnifier not working in Javascript

If the following function is called in node v0.10.26:

    function parseAndLog(constraint) {
        var constraintRegex = /\s*(.*?)\s*(<=|==|>=|[GL]?EQ)\s*(.*?)\s*(!required|!strong|!medium|!weak)?/;
        console.log(constraintRegex.exec(constraint));
    }

with the input:

"thumb.top == group.top + 20"

I expected that the following would be returned as substring matches (as happens when a similar function is called in Java)

thumb.top 
==
group.top + 20

But only the following is returned

thumb.top 
==

I hoped that "group.intrinsicHeight == preamble.bottom !medium" would yeild

group.intrinsicHeight
==
preamble.bottom
!medium

but only get the following

group.intrinsicHeight
==

I suspect the issue is something to do with the (.*?) group. I think this is known as a reluctant quantifier. Is it even supported by Javascript? If not, is there a workaround? Any help greatly appreciated.

I suggest you to use start and end anchors.

^\s*(.*?)\s*(<=|==|>=|[GL]?EQ)\s*(.*?)\s*(!required|!strong|!medium|!weak)?$

DEMO

String str = "thumb.top == group.top + 20\n" + 
             "group.intrinsicHeight == preamble.bottom !medium";
Matcher m = Pattern.compile("(?m)^\\s*(.*?)\\s*(<=|==|>=|[GL]?EQ)\\s*(.*?)\\s*(!required|!strong|!medium|!weak)?$").matcher(str);
while(m.find())
{
    if(m.group(1) != null)  { System.out.println(m.group(1)); }
    if(m.group(1) != null)  { System.out.println(m.group(2)); }
    if(m.group(1) != null)  { System.out.println(m.group(3));  }
    if(m.group(1) != null)  { System.out.println(m.group(4)); }
}

Because you described all the patterns except (<=|==|>=|[GL]?EQ) to repeat zero or more times. So it don't care about that there is a following (!required|!strong|!medium|!weak) or not, since you made this pattern as optional. By adding the start and end anchors, it ensures that the optional (!required|!strong|!medium|!weak) is followed by end of the line anchor. So regex engine tries to match upto the line end.

Adding start and end anchors made the regular expression behave as desired in Javascript

eg /^\\s*(.*?)\\s*(<=|==|>=|[GL]?EQ)\\s*(.*?)\\s*(!(required|strong|medium|weak))?$/;

Thanks to @avinash-raj for the suggestion.

If anybody could offer an explanation as to why this works and if the (.*?) group is in fact a "reluctant quantifier", I'd be grateful.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM