I am writing a program that reads the input from a file and then prints it to the screen. When I run it without taking the input from the file, it works perfectly fine. However, every time I try to run it from the file it gives me an "Exception in thread "main" java.util.NoSuchElementException: No line found at" error that occurs every place the input is suppose to be read. I have no idea what is going on.
This program is suppose to take the input from the user, create a Photo object, and then print the information to the screen. Everything runs fine when I am entering the information manually but when I try to use java PhotoTest < test.dat to get the input for a file it gives this error message:
Exception in thread "main" java.util.NoSuchElementException: No line found
at java.util.Scanner.nextLine(Scanner.java:1516)
at PhotoTest.readPhoto(PhotoTest.java:31)
at PhotoTest.main(PhotoTest.java:74)
My code that has input:
private static Photo readPhoto(Scanner scanner) throws ParseException
{
Date dateTaken;
Scanner scan = new Scanner(System.in);
String subject = scan.nextLine();
subject = subject.trim();
String location = scan.nextLine();
location = location.trim();
String date = scan.nextLine();
date = date.trim();
if (date.equals("")){ //if the date is empty it is set to null
dateTaken = null;
}
else { //if a date is entered, it is then parsed
DateFormat df = DateFormat.getDateInstance(DateFormat.SHORT);
dateTaken = df.parse(date);
}
String file = scan.nextLine();
file = file.trim();
File photoFile = new File(file);
//creates a Photo object from the information entered
Photo Photo = new Photo(subject, location, dateTaken, photoFile);
return Photo;
}
public static void main(String[] args) throws ParseException
{
boolean endprogram = false;
Scanner scan = new Scanner(System.in);
//creates a loop so that the user may enter as many photos as they wish
while (!endprogram)
{
System.out.println("Would you like to enter a photo (y/n)?");
//if the input is anything other than y, the program ends
if(!scan.next().equalsIgnoreCase("y"))
{
endprogram = true;
}
else
{
System.out.println(readPhoto(scan));
}
}
}
Everything runs fine when I am entering the information manually but when I try to use java PhotoTest < test.dat to get the input for[sic?] a file [...]
Does test.dat contain the "y" confirmations too? When you pipe in a file for stdin, the content of that file must be in legal format as if it was typed in manually.
Also, you are creating another Scanner instance for stdin even though one is already passed to readPhoto. Are you sure you need to do this?
In your file you need a carriage return in the last line. That would be the equivalent to what you are typing manually. Note that when you are typing, in the last line you press enter.
Related
The program I am writing needs to read 4 lines of data from a text file containing an ID, Name, Level, and Salary for an employee. It then needs to create a formatted email address and print all of this to standard output. The text file can contain an unknown number of employees, so a while loop must be used with the hasNext() method to confirm there is more data to read.
My program freezes (using Dr. Java) as soon as the while loop begins, and I cant figure out why.
Here is my code so far
public static void main(String[] args) throws IOException {
File file = new File("employeeInput.txt");
if (file.exists()) { //check if file exists
Scanner inputFile = new Scanner(file); //opens file
String companyName = inputFile.nextLine();
System.out.println(companyName);
System.out.println();
System.out.println("----------------------------");
while (inputFile.hasNext()); {
String studentID = inputFile.nextLine();
System.out.println(studentID);
String studentName = inputFile.nextLine();
System.out.println(studentName);
String employeeLevel = inputFile.nextLine();
System.out.println(employeeLevel);
double salary = inputFile.nextDouble();
System.out.println(salary);
}
inputFile.close();
}
else {
System.out.println("The file employeeInput.txt does not exist");
}
}
}
I understand this code is not complete and does everything the program needs to, but I do not get why it's freezing at the while loop..
Any help or advice would be appreciated. This is my first class ever in programming language, so go easy on me :)
I'm trying to implement the main method in java for a KWIC. The issue I'm having is that I have to ask the user if they want to write the input from the console/file and write the output to the console/file. The first time asking the user for console/file works fine when I have to read, but when I ask them again for the output I believe it goes back into the first If condition. Here is the code for reference.
try {
System.out.println("Please enter FILE to input from file or CONSOLE to input from console:");
String userInput = "";
while ((userInput = scannerWrapper.nextLine()) != "-1") {
if (userInput.equals("CONSOLE")) {
System.out.println("Please enter FILE to output from file or CONSOLE to output from console:");
List<String> cshiftConsole = circularShifter.shiftLines(inputFromConsole.read());
if (userInput.equals("CONSOLE")) {
System.out.println("Please enter lines to add, then enter -1 to finish:");
// Console
cshiftConsole = alphabetizer.sort(cshiftConsole);
outputToConsole.write(cshiftConsole);
for (String element : cshiftConsole) {
System.out.println(element);
}
}
}
}
} catch (Exception e) {
e.printStackTrace();
}
This is my console output
Please enter FILE to input from file or CONSOLE to input from console:
CONSOLE
Please enter FILE to output from file or CONSOLE to output from console:
CONSOLE
Software Architecture
-1
Please enter lines to add, then enter -1 to finish:
Architecture Software
CONSOLE
Software Architecture
After the second CONSOLE(userInput) I should be asked to enter the lines, But this is taking CONSOLE as the input I want to circularly shift. Any help would be great thank you.
You have some issues in your code, and if I understand correctly you want to decide where to INPUT from, where to OUTPUT to and get a couple of Strings into a List.
(userInput = scannerWrapper.nextLine()) != "-1" You compare Strings in Java using .equals(...) as you did in your code further below.
Every time you're asking your user where he wants to input from, you just have to read it once, so instead of having it inside a while do it on an if.
You create your list on every iteration, have it as an instance member instead.
On every iteration you're printing your objects, wait until the user stops adding items first (they type -1)
A better approach could be like this:
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
public class InputCycle {
private Scanner scanner;
private static final String CONSOLE = "CONSOLE";
private static final String EXIT_CODE = "-1";
private List<String> list;
public static void main(String[] args) {
new InputCycle().readAndWrite();
}
private void readAndWrite() {
scanner = new Scanner(System.in);
list = new ArrayList<String>();
System.out.println("INPUT FROM CONSOLE / FILE");
String input = scanner.nextLine(); // Read where to input from
if (input.equals(CONSOLE)) {
System.out.println("OUTPUT TO CONSOLE / FILE");
String output = scanner.nextLine(); // Read where to output to
if (output.equals(CONSOLE)) {
System.out.println("WRITE LINES (" + EXIT_CODE + " TO EXIT)");
String line = "";
do {
line = scanner.nextLine(); // Read every line
if (!line.equals(EXIT_CODE)) {
list.add(line);
}
} while (!line.equals(EXIT_CODE));
} else { // Write to a file with your own code
System.out.println("Writing to a file");
}
} else { //Read from a file
System.out.println("Reading from a file");
}
System.out.println("ALL LINES: ");
list.forEach(line -> System.out.println(line)); //Print all the lines user wrote
}
}
That has this output:
INPUT FROM CONSOLE / FILE
CONSOLE
OUTPUT TO CONSOLE / FILE
CONSOLE
WRITE LINES (-1 TO EXIT)
FOO
BAR
BANANA
-1
ALL LINES:
FOO
BAR
BANANA
Is there any possible way to accept a arbitrary(unknown) no. of input lines of string from the user until user explicitly enters -1 and store it in a string for further manipulation.
From what I gather, you're trying to get input from a user until that user types -1. If thats the case, please see my function below.
public static void main (String[] args)
{
// Scanner is used for I/O
Scanner input = new Scanner(System.in);
// Prompt user to enter text
System.out.println("Enter something ");
// Get input from scanner by using next()
String text = input.next();
// this variable is used to store all previous entries
String storage = "";
// While the user does not enter -1, keep receiving input
// Store user text into a running total variable (storage)
while (!text.equals("-1")) {
System.out.println("You entered: " + text);
text = input.next();
storage = storage + "\n" + text
}
}
I've left comments in that code block but I'll reiterate it here. First we declare our I/O object so that we can get input from the keyboard. We then ask the user to "Enter something" and wait for the user to enter something. This process is repeated in the while loop until the user specifically types -1.
Your question makes no sense... You're talking about taking input from a user, but also reaching the end of a file, implying you are taking reading input from a file. Which is it?
If you're trying to say that for each line in a file, the user must enter something for some action to be taken, then yes, that can be done.
I'll assume you already have a File object or String containing the file path, named file.
// make a stream for the file
BufferedReader fileReader = new BufferedReader(new FileReader(file));
// make a stream for the console
BufferedReader consoleReader = new BufferedReader(new InputStreamReader(System.in));
// declare a String to store the file input
String fileInput;
// use a StringBuilder to construct the user input lines
StringBuilder inputLines = new StringBuilder();
// while there is a line to be read
while ((fileInput = fileReader.readLine()) != null) {
/*
** maybe some output here to instruct the user?
*/
// get some input from the user
String userInput = consoleReader.readLine();
// if the user wants to stop
if (userInput.equals("-1")) {
// exit the loop
break;
}
// else append the input
inputLines.append(userInput+"\r\n");
}
// close your streams
fileReader.close();
consoleReader.close();
// perform your further manipulation
doSomething(inputLines.toString());
Those classes are located in java.io.*. Also, remember to catch or have your method throw IOException.
If you want to perform your manipulation each time you have some input instead of doing it all at the end, get rid of the StringBuilder, and move doSomething(userInput) into the loop before the if statement.
I had a quick questions about prompting and accepting a file name, then making the file-text a scanner object.
I want the program to prompt the user to enter the name of a file, until he gets one which exists, then for the file-text to be used as a scanner object.
This is the code I have so far, it works to the point where I exit the while {} loop, but then when I try and process the scanner item like while (input.hasNextLine()) { it gives me an error saying it can't find the scanner item.
It's probably a silly mistake, but I just cannot seem to get it.
The whole code is below:
import java.io.*;
import java.util.*;
public class PersonalityTest {
public static void main(String[] args) throws FileNotFoundException {
boolean isFile = false;
Scanner sc = new Scanner(System.in);
System.out.print("Input file name? ");
String fileName = sc.next();
File inputFile = new File(fileName);
while (isFile == false) {
if (inputFile.exists()) {
Scanner input = new Scanner(inputFile);
isFile = true;
}
}
while(input.hasNextLine()) {
}
}
The scope of the input variable is local to the while (isFile == false) block. Declare it outside otherwise it won't be visible.
For the first part "I want the program to prompt the user to enter the name of a file, until he gets one which exists": Move this code:
Scanner sc = new Scanner(System.in);
System.out.print("Input file name? ");
String fileName = sc.next();
File inputFile = new File(fileName);
into a method and call it inside the while (isFile == false) block before the exists check (the method should return with the file or make the variable visible in the block by some other means).
You can't access input outside the if statement, sice the compiler is not sure, it will pass the test, you can do this:
Scanner sc = new Scanner(System.in);
Scanner input = null;
boolean isFile = false;
while (isFile == false){
System.out.print("Input file name? ");
String fileName = sc.next();
File inputFile = new File(fileName);
if (inputFile.exists()){
input = new Scanner(inputFile);
isFile = true;
}
}
But will throw a NullPointerException if it is null.
I changed the code a little bit, that way, it will not exceed if the file doesn't exist.
The Scanner input is local to your if statement. Your while (input.hasNextLine()) { statement will not work because of that. The Java compiler will treat input as a separate Scanner object and that is where the problems crop up, because to the Java compiler, the input that you are trying to use does not exist.
I would follow MouseEvent's suggested code as it does not run into the problem mentioned above.
The other answers have addressed your immediate question, but I want to point out a couple of other problems with your code:
The way that you are checking to see if the file can be opened is flawed. A better way to write the code is to attempt to open the file ... and retry when there is an exception. For example:
Scanner input = null;
do {
System.out.print("Input file name? ");
String fileName = sc.next();
File inputFile = new File(fileName);
try {
input = new Scanner(inputFile);
} catch (IOException ex) {
System.out.println("Cannot open: " + ex.getMessage());
}
} while (input == null);
Why is this better than calling File.exists()?
There are lots of reasons why you might be able to open a file. It might not exist at all. It might be a directory or a special file that can't be opened as a file. The application might not have permission. The file might be on a remote mounted file system and the remote mount might have just died.
There is a small time gap between the File.exists() call (and any others that you might make) and actually opening the file. In that time gap, it is possible that something to your program could do something to make the file unopenable; e.g. it could change its permissions or delete it.
The second problem is that your code potentially leaks a file descriptor because the scanner is not closed. In your specific application (as written) this doesn't matter because you are going to exit the application immediately after using the scanner. But if your weren't ... and this code was called lots of times ... you could find that you are unable to open files after a bit.
The correct way to deal with this would be to write your code something like this:
public static void main(String[] args) {
try (Scanner input = openInput()) {
while (input.hasNextLine()) {
// do stuff
}
}
}
This uses Java 7's new "try with resource" syntax, that ensures that the resource is closed when the try statement completes. (You can do the same thing in pre-Java 7 using a try / finally, but the code is a bit more cumbersome.)
I am trying to find a way to deal with the NoSuchElementException error thrown by a Scanner object when reading the last item in my text file with NO SPARE LINE. This means that my cursor will end after the last character of the last line in the file
EXAMPLE:
score.txt
[Test;Word|]
[ & ] denotes the start and end of the text file
The | is where the cursor ends.
I know that if my cursor ends a line below it, my Scanner will not throw the NoSuchElementException because there is a nextLine.
What i want to achieve is to ensure that the NoSuchElementException is not thrown when the spare line is missing. Is there a way to prevent the error from occurring besides making sure that the spare line is there?
My Driver class simply calls the method importWordList() from class WordGame.
The code for WordGame is very long so I will only upload the method importWordList() from the class.
public boolean importWordList(String fileName) throws FileNotFoundException
{
//Set default return value
boolean returnVal = false;
//Set File to read from
File wordListDest = new File(fileName);
if (wordListDest.canRead() == true)
{
lineS = new Scanner(wordListDest);
//Read each line from file till there is no line
while (lineS.hasNextLine())
{
//Set delimeter scanner to use delimeter for line from line scanner
String line = lineS.nextLine();
delimeterS = new Scanner(line);
delimeterS.useDelimiter(";");
//Read each delimeted string in line till there is no string
while (delimeterS.hasNextLine())
{
//Store Variables for quiz object
wordAndHint = delimeterS.nextLine();
answer = delimeterS.nextLine(); //ERROR
//Create Object Quiz and add to wordList
Quiz addWord = new Quiz(wordAndHint, answer);
wordList.add(addWord);
}
delimeterS.close();
}
lineS.close();
returnVal = true;
System.out.println("Word List has been Imported Successfully!");
}
else
{
System.out.println("The file path you selected either does not exist or is not accessible!");
}
return returnVal;
}
The Error that occurs is as Follows:
Exception in thread "main" java.util.NoSuchElementException: No line found
at java.util.Scanner.nextLine(Scanner.java:1516)
at mysterywordgame.WordGame.importWordList(WordGame.java:74)
at mysterywordgame.Main.main(Main.java:60)
The error (at mysterywordgame.WordGame.importWordList(WordGame.java:74)) refers to line with the comment ERROR.
I have searched around for ways to prevent the error from occurring, however, all answers were "Make sure there is a spare line at the end of the text file"
Some help will be much appreciated.
As you already consumed the next line with wordAndHint = delimeterS.nextLine(); you have to check for next line again:
if(delimeterS.hasNextLine()){
answer = delimeterS.nextLine();
}else{
answer = "";
}