2015-05-04 3 views
2

У меня есть проблема, по которой я не могу найти ответ здесь, поэтому я прошу об этом.Java String split regexp возвращает пустые строки с несколькими разделителями

Дело в том, что у меня есть строка, и у меня есть разделители. Я хочу создать массив строк из вещей, которые находятся между этими разделителями (могут быть слова, числа и т. Д.). Однако, если у меня есть два разделителя рядом друг с другом, метод split возвращает пустую строку для одного из экземпляров.

Я проверил это против еще большего числа разделителей, которые последовательно. Я узнал, что если у меня есть n разделителей, у меня будет n-1 пустых строк в массиве результатов. Другими словами, если у меня есть и «» и „“ в качестве разделителей и предложения „Это очень хороший день, не правда ли“, то массив с результатами будет, как:

{... , "day", "", "isn't" ...} 

Я хочу получить эти лишние пустые строки, и я не могу понять, как это сделать. Образец регулярного выражения для разделителей, что у меня есть это:

"[\\s,.-\\'\\[\\]\\(\\)]" 

Также вы можете объяснить, почему есть лишние пустые строки в результирующем массиве?

P.S. Я прочитал некоторые аналогичные записи, которые включали информацию о втором параметре регулярного выражения. Я пробовал как отрицательные, нулевые, так и положительные числа, и я не получил результат, который я ищу. (один из вопросов имел ответ, говорящий, что -1 в качестве параметра может решить проблему, но это не так.

+0

Так что же ваш код? – isnot2bad

+0

это не связанный код, я думаю, что проблема связана с параметрами или с тем, как String использует Pattern и Matcher для создания массива результатов. – Mackiavelli

ответ

1

Вы можете использовать это регулярное выражение для расщепления:

[\\s,.'\\[\\]()-]+ 
  • Держите неэкранированный дефис в первый или последний позиции в классе символов, в противном случае он рассматривается как диапазон, такой как A-Z или 0-9
  • Вы должны использовать квантор + для согласования более 1 разделителей
+0

Причина, по которой дефис является первым/последним? – Mackiavelli

+0

Добавлено более подробную информацию об этом также – anubhava

+0

Да, но поскольку это разделитель для диапазона, было бы лучше, если бы вы espcaped дефис или что-то еще? – Mackiavelli

1

Ваше регулярное выражение описывает только один символ. Если вы хотите, чтобы он соответствовал нескольким разделителям одновременно, использовать квантор:

String s = "This is a very nice day, isn't it"; 
String[] tokens = s.split("[\\s,.\\-\\[\\]()']+"); 

(Обратите внимание на «+» в конце выражения)

+0

Я понятия не имел, что я могу использовать +, как в регулярном regexp, спасибо – Mackiavelli

0

Если вы хотите, чтобы избавиться от пустых строк, вы можете использовать проект Splitter класса Guava.

on метод:

Возвращает разделитель, который использует заданную фиксированную строку в качестве разделителя.

Пример (игнорируя пустые строки):

System.out.println(
       Splitter.on(',') 
        .trimResults() 
        .omitEmptyStrings() 
        .split("foo,bar,, qux") 
       ); 

Выход:

[foo, bar, qux] 

onPattern метод:

возвращает splitter, который считает, что любая подпоследовательность, соответствующая заданному шаблону (регулярное выражение), является разделителем.

Пример (игнорируя пустые строки):

System.out.println(
       Splitter 
       .onPattern("([,.|])") 
       .trimResults() 
       .omitEmptyStrings() 
       .split("foo|bar,, qux.hi") 
       ); 

Выход:

[foo, bar, qux, hi] 

Для получения более подробной информации, обратитесь к Splitter documentation.

+0

@Mackiavelli Вы пытались использовать класс Splitter? Вот [документация] (http://docs.guava-libraries.googlecode.com/git/javadoc/com/google/common/base/Splitter.html). – MChaker

Смежные вопросы