3

I have the String

shape="box", fontsize = "130"fontstyle= " ITALIC " fillcolor=red";

and the pattern

"(([^\\s,]+)((\\s*)=(\\s*)\"(.+?)\"))"

which currently matches

shape="box"
fontsize = "130"
fontstyle= " ITALIC "

as intended.

I need those matching strings separated and stored in an array. The easiest way I thought of was using String.split(inverted pattern), however I quickly realized that matching the inverse of a specific pattern, that is everything but this pattern, seems to be quite a hard task. So far, I couldn't find a method working for me.

For some reason, neither negative-lookahead, nor

^((?!pattern).)*$

(which I've often seen given as the solution to my problem) seem to be working.

Is there any way to do this I'm not seeing right now?

  • Simplest way would be putting found data in List instead of array. If you want then you can later move that data to array, but usually Lists are easier to work with. – Pshemo Oct 20 '17 at 14:34
  • You seem to be parsing attributes of a markup node. You're probably better off not using regex and using a markup parser instead. – Mena Oct 20 '17 at 14:34
  • I had a problem, I try to solve it with regexp, now I have two problems. Sad, but true. Try to use this web service - https://regex101.com/ – degr Oct 20 '17 at 14:48

1 Answers1

1

Making a pattern for a delimiter in your case is not practical, because it requires odd-even counting outside your pattern - something Java regex has hard time doing.

Your string is a perfect example: a single space is a separator when it is preceded by an even number of doublequotes; otherwise, it is part of a quoted value.

Rather than trying to make your expression suitable for use with split() method, make a pattern matcher, and call it repeatedly to parse your string into matching chunks. This Q&A explains how to do it with very little code.

List<String> chunks = new ArrayList<>();
Matcher m = Pattern.compile("(([^\\s,]+)((\\s*)=(\\s*)\"([^\"]+)\"))")
     .matcher("shape=\"box\", fontsize = \"130\"fontstyle= \" ITALIC \" fillcolor=\"red\";");
while (m.find()) {
     chunks.add(m.group());
}
Sergey Kalinichenko
  • 714,442
  • 84
  • 1,110
  • 1,523
  • *"Making a pattern for a delimiter in your case is not practical, because it requires odd-even counting outside your pattern"*: The best and more concise description of the problem I have ever read. – Casimir et Hippolyte Oct 20 '17 at 22:27