Search code examples
regexregex-group

How to only use input in pattern once?


regex = ^(movie|tv) (.*) (?<=season )([0-9 ]+)

input = tv game of thrones season 1 2 3

output

tv
game of thrones season
1 2 3

desired output

tv
game of thrones
1 2 3

https://regex101.com/r/wG3aM3/954

(.*) captures all string before ([0-9 ]+) how can i prevent it from capturing (?<=season ) which is before ([0-9 ]+).

P.S i cant just negate "season" from (.*) . i.e tv game of season season 1 2 3 should capture tv game of season 1 2 3


Solution

  • You can use

    ^(movie|tv)\s*(.*?)(?:\s+season)?(?:\s+([0-9]+(?:\s+[0-9]+)*))?$
    

    See the regex demo.

    Details

    • ^ - start of string
    • (movie|tv) - Group 1: movie or tv
    • \s* - zero or more whitespaces
    • (.*?) - Group 2: any zero or more chars other than line break chars as few as possible
    • (?:\s+season)? - an optional non-capturing group matching one or more whitespaces followed with season string
    • (?:\s+([0-9]+(?:\s+[0-9]+)*))? - an optional non-capturing group matching
      • \s+ - one or more whitespaces
      • ([0-9]+(?:\s+[0-9]+)*) - Group 3: one or more digits followed with zero or more repetitions of one or more whitespace chars followed with one or more digits
    • $ - end of string.