#java #file #file-io #java.util.scanner
#java #файл #file-io #java.util.scanner
Вопрос:
Проблема
В настоящее время я создаю программу для чтения файла и поиска пары переменных. Я сталкиваюсь с этой проблемой, когда изменение одного println изменяет весь вывод моего кода. Я никогда не сталкивался с этим раньше и не уверен, является ли это ошибкой eclipse или моей ошибкой?
Мой код
import java.io.File;
import java.io.IOException;
import java.util.Scanner;
public class FileAnalyzer {
public static void main(String args[]) throws IOException {
Scanner input = new Scanner(System.in);
String fileName;
int words = 0, letters = 0, blanks = 0, digits = 0, miscChars = 0, lines = 0;
System.out.print("Please enter the file path of a .txt file: ");
fileName = input.nextLine();
File text = new File(fileName);
//System.out.println(text.exists());
Scanner word = new Scanner(text);
while(word.hasNext()) {
//System.out.println(word.next());
words ;
}
word.close();
Scanner letter = new Scanner(text);
while(letter.hasNext()) {
String currentWord = letter.next().toLowerCase();
for(int i = 0; i < currentWord.length(); i ) {
if(Character.isLetter(currentWord.charAt(i))) {
letters ;
}
}
}
letter.close();
Scanner blank = new Scanner(text);
while(blank.hasNextLine()) {
String currentWord = blank.nextLine();
for(int j = 0; j < currentWord.length(); j ) {
if (currentWord.charAt(j) == ' ') {
blanks ;
}
}
}
blank.close();
System.out.println("Words: " words);
System.out.println("Letters: " letters);
System.out.println("Blanks: " blanks);
}
}
Однако
Простое изменение System.out.println(word.next())
в первом экземпляре сканера изменяет весь вывод. Если я оставлю это, я получу три оператора печати внизу и то, что я ищу. Если я удалю его, поскольку я не хочу, чтобы каждое слово печаталось в файле, оно не отображается как ничто в консоли. Не уверен, почему один оператор печати в операторе while изменяет весь вывод.Единственная причина, по которой он был там в первую очередь, заключалась в том, чтобы убедиться, что сканер принимает входные данные так, как я хотел.
Ответ №1:
Не уверен, почему один оператор печати в операторе while изменяет весь вывод
Потому что, когда оператор присутствует, вы потребляете токен из сканера. Когда он закомментирован, вы этого не делаете. Токен потребляет не печать, а вызов next()
.
После того, как он закомментирован, ваш цикл:
while (word.hasNext()) {
words ;
}
hasNext()
не изменяет состояние сканера, так что он будет просто зацикливаться вечно, если вообще попадет в тело цикла.
Если вы хотите иметь строку, которую вы можете закомментировать или нет, измените код на:
while (word.hasNext()) {
String next = word.next(); // Consume the word
System.out.println(next); // Comment this out if you want to
words ;
}
Комментарии:
1. @IanHank: Да, это было бы к лучшему, хотя на самом деле это ортогонально вопросу.
Ответ №2:
С помощью System.out.println(word.next());
вы перебираете элементы в коллекции из-за next()
метода. Таким образом, вызов next()
напрямую позволит вам перемещаться по итерации.
При комментировании //System.out.println(word.next());
это word.hasNext()
приведет к бесконечному циклу (при условии, что есть слово), поскольку вы не сможете перейти к следующему токену.
Приведенный ниже фрагмент поможет вам достичь желаемого результата
while(word.hasNext()){
word.next();
words ;
}
Ответ №3:
Не уверен, почему вы хотели бы просмотреть текст три раза. Но если вам действительно нужно, я бы закрыл первый сканер перед открытием следующего.
Комментарии:
1. Хотя в целом это хорошая идея, я не думаю, что это отвечает на вопрос о том, почему код ведет себя по-другому с закомментированным оператором.
2. Обычно я бы этого не сделал, но учитель хочет, чтобы мы это сделали, чтобы мы попрактиковались, я думаю? На самом деле я закрыл все три сразу после публикации и подумал, что кто-нибудь прокомментирует это.