How to create a dynamic capture group in a regular expression?

I have a line like this:

$str =" - group1 - group2 - group3 "; 

I also have regex :

 /(\-\s\w+)\n(\-\s\w+)\n(\-\s\w+)/ 

As you know, there are three capture groups: $1 , $2 and $3 . I made this group manually. I mean, if I add this to the line above:

 - group4 - group5 

Then this regular expression does not match them.


Well, I have a constant pattern: (\-\s\w+) , and I want to create a separate capture group by the number of matching elements in the row. The applicant is a few examples:

Example 1:

 $str=" - group 1 "; 

I need a regex to pass me the entire line of $1 .


Example 2:

 $str=" - group 1 - group 2 "; 

I need a regular expression to pass me the first line of the line ( - group 1 ) to $1 and the second line ( - group 2 ) to $2


Well, as you see in the examples above, the line is dynamic, but it matches a constant pattern ... Now I want to know how to create a dynamic capture group according to the line?

+6
source share
2 answers

The inability to capture duplicate groups is a known limitation .

If you know the max repeating pattern, you can set the regex as (i.e. max = 5):

 /(\-\s\w+)\n(\-\s\w+)?\n?(\-\s\w+)?\n?(\-\s\w+)?\n?(\-\s\w+)?\n?/ 

and you will find one to five matches in groups of 1 to 5.
Essentially, you need to repeat (\-\s\w+)?\n? for the maximum possible number of repeating patterns.

Otherwise, if your maximum number is undefined, I don’t know of any other way but to build a dynamic template, for example:

 $regex = '(\-\s\w+)\n'; $regex = '/'.( str_repeat( $regex, preg_match_all( "/$regex/", $str, $matches ) ) ).'/'; 

The above pattern will work, but I don’t know what you are replacing for sure, so it may not be suitable for your purpose.

+1
source

Using m-modifier (multi-line): this will allow a match on each line.

Try using the regex below:

  preg_match_all('/(\-\s\w+)/m', $str, $matches); print_r($matches); 
+1
source

All Articles