Самый простой способ - использовать двухэтапное решение: 1) сначала проверьте строку, затем 2) разбейте строку с помощью выбранного вами разделителя:
String[] chunks = null;
if (s.matches("\\d{2}(?:,\\d{2})*")) {
chunks = s.split(Pattern.quote(","));
System.out.println(Arrays.toString(chunks)); // => [12, 34, 98, 11]
}
Здесь s.matches("\\d{2}(?:,\\d{2})*")
соответствует всей строке, которая начинается с двух цифр, а затем содержит 0 или более вхождений ,
и двух цифр до конца, а затем s.split(Pattern.quote(","))
разделяет строку запятой. Обратите внимание, что вам не нужны якоря ^
и $
с шаблоном внутри matches()
, поскольку метод требует полного совпадения строк.
Если вам нужно сделать это с одним регулярным выражением , вы можете использовать несколько совпадений, привязанных к началу строки и концу каждого успешного предыдущего совпадения, только если проверка строки в начале строки прошла успешно:
(?:\G(?!^),|^(?=\d{2}(?:,\d{2})*$))(\d{2})
См. regex demo .
Подробности
(?:\G(?!^),|^(?=\d{2}(?:,\d{2})*$))
- конец предыдущего успешного матча и затем ,
(см. \G(?!^),
) или (|
) начало строки (^
), за которой следуют две цифры, а затем 0 или более последовательностей ,
и двух цифр до конца строки (см. \d{2}(?:,\d{2})*$
) (\d{2})
- Группа 1: две цифры
Java демо :
String s = "12,34,98,11";
Pattern p = Pattern.compile("(?:\\G(?!^),|^(?=\\d{2}(?:,\\d{2})*$))(\\d{2})");
Matcher m = p.matcher(s);
List<String> results = new ArrayList<>();
while(m.find()) {
results.add(m.group(1));
}
System.out.println(results);
// => [12, 34, 98, 11]