Как сканировать слова в Java, исключая знаки препинания

#java #parsing

#java #синтаксический анализ

Вопрос:

Я пытаюсь использовать класс scanner для анализа всех слов в файле. Файл содержит обычный текст, но я хочу использовать только слова, исключая все знаки препинания. Решение, которое у меня есть до сих пор, не завершено, но уже вызывает у меня некоторые проблемы:

 Scanner fileScan= new Scanner(file);
String word;
while(fileScan.hasNext("[^ ,!?.] ")){       
    word= fileScan.next();
    this.addToIndex(word, filename);
}
  

Теперь, если я использую это в предложении типа «привет, меня зовут Марио!», он возвращает только «привет», «мой», «имя» и «есть». Это не соответствует «марио!» (очевидно), но это не соответствует «марио», как я думаю, должно быть.

Можете ли вы объяснить, почему это так, и помочь мне найти лучшее решение, если оно у вас есть? Спасибо

Комментарии:

1. Как насчет чего-то подобного Dr. Mario's ?

2. Как getNextWord определяется?

Ответ №1:

Это работает:

импортируйте java.util.*;

 class S {

    public static void main(String[] args) {
        Scanner fileScan= new Scanner("hi my name is mario!").useDelimiter("[ ,!?.] ");
        String word;
        while(fileScan.hasNext()){       
            word= fileScan.next();
            System.out.println(word);
        }

    } // end of main()
}


javac -g S.java amp;amp; java S
hi
my
name
is
mario
  

Комментарии:

1.Потому что next(pattern) возвращает следующий токен, если он соответствует указанному шаблону. Последний токен (с разделителями по умолчанию) "Mario!" , который не соответствует "[^ ,!?.] "

2. Спасибо, теперь я понимаю next() намного лучше!

Ответ №2:

Поскольку вы хотите избавиться от знаков препинания, вы можете просто заменить все знаки препинания перед добавлением в индекс:

 word = word.replaceAll("\{Punct}", "");
  

В случае дефисов или других изолированных знаков препинания вы просто проверяете, если word.isEmpty() перед добавлением.

Конечно, вам придется избавиться от вашего пользовательского разделителя.

Комментарии:

1. Для последнего токена, "mario!" , fileScan.hasNext("[^ ,!?.] ") вернет false . Так word.replaceAll("\{Punct}", ""); что не будет выполнено, правильно? OP все равно не доберется до Марио.

2. @Hemal Pandya — я имел в виду использовать разделитель по умолчанию — пробел, а не его пользовательский

3. Из вашего ответа неясно, что не только word.replaceAll() должно быть сделано, но fileScan.hasNext и должно быть изменено. Было бы неплохо, если бы вы могли отредактировать свой ответ, но я думаю, что этот обмен комментариями также проясняет это.