0

Given Input:

{abcd} {{abcd}} {{{abcd}}}

How can I extract texts which are surrounded by either single braces or triple braces? I don't text if double braces surround it.

Output:

{abcd} {abcd}

The second {abcd} in the output is extraced from {{{abcd}}}

Do you have any ideas?

  • If you just need to extract what's inside and input is always like your sample, it's probably enough to just verify the closing braces: [`[^}{]+(?=}(?:}})?(?!}))`](https://regex101.com/r/lZqmri/4) – bobble bubble Nov 07 '19 at 09:28

3 Answers3

1

You can try to use regex to define the pattern.

Logic

  • Start looking for pattern if { or {{{ is either start of string or is preceded by space.
  • Capture any string until } or }}}

You will have to use non-capturing(?:) groups to define the start and end.

var str = '{abcd} {{efgh}} {{{ijkl}}}';
var regex = /(?:^| )(?:\{|\{{3})(\w+)(?:\}|\}{3})/g

console.log(str.match(regex))

References:

Community
  • 1
  • 1
Rajesh
  • 24,354
  • 5
  • 48
  • 79
  • **Note:** If you think there is anything *inaccurate/ missing*, please share your views along with your vote. Also, There can be better a regex using boundaries(`\b`) but not sharing as even I have little knowledge in it. – Rajesh Nov 07 '19 at 07:32
1

In case you want a non-regEx solution, please check this out. I have tried to make it as simple and extensive as possible using common JS methods like: Array.fill() and String.split()

function textExtractor(input, startChar, endChar, count, ignoreFlag) {
  let startExpression = new Array(count).fill(startChar).join("");
  let endExpression = new Array(count).fill(endChar).join("");
  if (ignoreFlag) return input;
  else return input.split(startExpression)[1].split(endExpression)[0];
}

console.log(textExtractor("{abc}", "{", "}", 1, false));
console.log(textExtractor("{{abc}}}", "{", "}", 2, true));
console.log(textExtractor("{{{abc}}}", "{", "}", 3, false));
sibasishm
  • 443
  • 6
  • 24
1

If you're not obsessed with performance, doing it in 2 .replaces() makes it very easy :

"{abcd} {{abcd}} {{{abcd}}}".replace(/(\s|^){{\w+}}/g,'').replace(/{{({\w+})}}/g, '$1')

1st step replace(/(\s|^){{\w+}}/g,'') removes {{ }} elements

2nd step replace(/{{({\w+})}}/g, '$1') transforms {{{ }}} to { }

Vincent
  • 3,945
  • 3
  • 13
  • 25
  • I don't want to remove {{ }} I just want to replace these { } {{{ }}} – Shivam Sinha Nov 07 '19 at 09:06
  • You told us that things like {{abcd}} should be removed because you want to keep only items like  {abcd} and {{{abcd}}}, so this is what my code does: if you try to execute "{test1} {{test2}} {{{test3}}}".replace(/(\s|^){{\w+}}/g,'').replace(/{{({\w+})}}/g, '$1') then you will get this output: "{test1} {test3}" – Vincent Nov 07 '19 at 09:23