skip to Main Content

I want to take all of the substrings inside of string which is between given two regex. Couple examples:

My $$name$$ is John, my $$surname$$ is Doe -> should return [name, surname]

My &&name&& is John, my &&surname&& is Doe -> should return again [name, surname]

I have tried couple solutions but non of them works for multiple substring with given dynamic values. How can I do that?

3

Answers


  1. Use this regex : (?<=$$|&&)(w+)(?=$$|&&)

    Explanation :

    (?<=r)d : matches a d only if is preceded by an r, but r will not be part of the overall regex match.

    d(?=r) : matches a d only if is followed by r, but r will not be part of the overall regex match.

    const regex = /(?<=$$|&&)(w+)(?=$$|&&)/gm;
    
    const str = "My $$name$$ is John, my $$surname$$ is Doe";
    let m;
    
    while ((m = regex.exec(str)) !== null) {
        // This is necessary to avoid infinite loops with zero-width matches
        if (m.index === regex.lastIndex) {
            regex.lastIndex++;
        }
        
        // The result can be accessed through the `m`-variable.
        m.forEach((match, groupIndex) => {
            if (groupIndex > 0)
            console.log(match);
        });
    }
    Login or Signup to reply.
  2. I would use this:

    /(?<=$$)[w_]+(?=$$)|(?<=&&)[w_]+(?=&&)/g
    

    https://regex101.com/r/j4iR9O/2

    The idea is to use two patterns (one for $$ and one for &&).
    This can be done with the | syntax.

    Then, I’m using a positive lookbehind (?<= ) to search for the $$ that
    I have to escape with a slash because $ has a meaning in regular expressions.

    For the positive lookahead, it’s (?= ).

    In the middle, I want to match any word character or underscores (as it’s a
    variable name). This leads to [w_]+ meaning word char or underscores, at
    least once or several times.

    const regex = /(?<=$$)[w_]+(?=$$)|(?<=&&)[w_]+(?=&&)/g;
    
    const str = `My $$name$$ is John, my $$surname$$ is Doe -> should return [name, surname]
    My &&name&& is John, my &&surname&& is Doe -> should return again [name, surname]`;
    let m;
    
    while ((m = regex.exec(str)) !== null) {
        // This is necessary to avoid infinite loops with zero-width matches
        if (m.index === regex.lastIndex) {
            regex.lastIndex++;
        }
        
        // The result can be accessed through the `m`-variable.
        m.forEach((match, groupIndex) => {
            console.log(`Found match, group ${groupIndex}: ${match}`);
        });
    }
    Login or Signup to reply.
  3. Using regular expression groups you can extract the values between a specified delimiter and then capturing a group in between those delimiters.

    Works by creating a regex such as $$(w+)$$ using the specified delimiter.

    function matchSubstrings(input, delim) {
      // Used to escape regex operators, works by wrapping the token
      // in a [] (set). Prepending a  is problematic.
      function escape(unescaped) {
        return unescaped.split("").map(v => `[${v}]`).join("");
      }
     
      const escapedDelim = escape(delim);
      return [...input.matchAll(new RegExp(`${escapedDelim}(\w+)${escapedDelim}`, "g"))]?.map(v => v[1]) ?? [];
    }
    
    console.log(matchSubstrings("My $$name$$ is John, my $$surname$$ is Doe", "$$"));
    console.log(matchSubstrings("My &&name&& is John, my &&surname&& is Doe", "&&"));
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search