I am writing a program where I create an ArrayList, and I want to traverse the list with an iterator:
ArrayList<Person> flightAttendants = new ArrayList<Person>();
Iterator<Person> itr = flightAttendants.iterator();
Here is how I am trying to traverse the elements of the arraylist:
I have defined a toString method too:
while(itr.hasNext())
{
System.out.println(itr.next());
}
public String toString()
{
System.out.println("name of the passenger : "+name);
System.out.println("Age of the passenger : "+age);
System.out.println("Seat number of the passenger : "+seatNumber);
return "\n";
}
Whenever I try to run it, it gives me the error: java.util.ConcurrentModificationException
Where is the error here?
Update: here is the full code:
import java.util.*;
import java.io.*;
class Person
{
Integer age;
String name;
String seatNumber;
Integer fare;
int pnr;
Person()
{
try
{
BufferedReader b = new BufferedReader(new InputStreamReader(System.in));
System.out.println("Enter the name of the passenger");
name = b.readLine();
System.out.println("Enter the age of the passenger");
age = Integer.parseInt(b.readLine());
System.out.println("Enter the Seat Number you want");
seatNumber = b.readLine();
pnr = (int)(Math.random()*100000000);
System.out.println("PNR number of the passenger is : "+pnr);
}
catch(Exception e)
{
System.out.println("");
}
}
public String toString()
{
System.out.println("name of the passenger : "+name);
System.out.println("Age of the passenger : "+age);
System.out.println("Seat number of the passenger : "+seatNumber);
return "\n";
}
}
class EconomyPassenger extends Person
{
}
class BusinessPassenger extends Person
{
}
class Crew extends Person
{
}
public class Airline
{
public static void main(String[] args)
{
ArrayList<Person> flightAttendants = new ArrayList<Person>();
Iterator<Person> itr = flightAttendants.iterator();
while(true)
{
try
{
System.out.println("Welcome to Indigo!!!");
BufferedReader b = new BufferedReader(new InputStreamReader(System.in));
System.out.println("Enter your Choice");
System.out.println("1.Book Tickets");
System.out.println("2.Check Reservation");
System.out.println("3.Update Tickets");
System.out.println("4.Exit");
int choice=Integer.parseInt(b.readLine());
if(choice<0 || choice>4)
{
throw new InvalidChoiceException("Enter a valid choice between 1 and 4");
}
switch(choice)
{
case 1: System.out.println("\n\n1.Economy*******2.Business*******3.Crew Login*******4.Exit");
// BufferedReader c = new BufferedReader(new InputStreamReader(System.in));
int c = Integer.parseInt(b.readLine());
if(c==1)
{
flightAttendants.add(new EconomyPassenger());
}
else if(c==2)
{
flightAttendants.add(new BusinessPassenger());
}
else if(c==3)
{
flightAttendants.add(new Crew());
}
else if(c==4)
{
break;
}
break;
case 2: // System.out.println("Enter your PNR Number : ");
// int p = Integer.parseInt(b.readLine());
// System.out.println(p);
while(itr.hasNext())
{
System.out.println(itr.next());
}
break;
case 3: System.out.println("case 3");break;
case 4: return;
default: System.out.println("default");
}
}
catch(InvalidChoiceException ic)
{
// System.out.println(ic);
}
catch(Exception e)
{
System.out.println(e);
}
}
}
}
class InvalidChoiceException extends Exception
{
InvalidChoiceException()
{}
InvalidChoiceException(String msg)
{
System.out.println(msg);
}
}
The code being provided by you should work fine as I have tried it. Unless you show there is something else your code is working upon we cant further try to solve. I suggest you the check the question Iterators and the concurrentmodificationexception also for better understanding that your code may be somewhere falling into errors mentioned there.
As mentioned by Andrew bring the iterator into your while loop and thats working fine check now. I tried it.
Related
Here is my code:
import java.util.LinkedList;
import java.util.Scanner;
import java.util.InputMismatchException;
import java.util.*;
class Customer {
public String lastName;
public String firstName;
public Customer() {
}
public Customer(String last, String first) {
this.lastName = last;
this.firstName = first;
}
public String toString() {
return firstName + " " + lastName;
}
}
class HourlyCustomer extends Customer {
public double hourlyRate;
public HourlyCustomer(String last, String first) {
super(last, first);
}
}
class GenQueue<E> {
private LinkedList<E> list = new LinkedList<E>();
public void enqueue(E item) {
list.addLast(item);
}
public E dequeue() {
return list.poll();
}
public boolean hasItems() {
return !list.isEmpty();
}
public boolean isEmpty()
{
return list == null;
}
public E removeFirst(){
return list.removeFirst();
}
public E getFirst(){
return list.getFirst();
}
public int size() {
return list.size();
}
public void addItems(GenQueue<? extends E> q) {
while (q.hasItems()) list.addLast(q.dequeue());
}
}
public class something {
public static void main(String[] args){
while(true){
Scanner sc = new Scanner(System.in);
String input1;
String input2;
int choice = 1000;
GenQueue<Customer> empList;
empList = new GenQueue<Customer>();
GenQueue<HourlyCustomer> hList;
hList = new GenQueue<HourlyCustomer>();
do{
System.out.println("================");
System.out.println("Queue Operations Menu");
System.out.println("================");
System.out.println("1,Enquene");
System.out.println("2,Dequeue");
System.out.println("0, Quit\n");
System.out.println("Enter Choice:");
try{
choice = sc.nextInt();
switch(choice){
case 1:
do{
System.out.println("\nPlease enter last name: ");
input1 = sc.next();
System.out.println("\nPlease enter first name: ");
input2 = sc.next();
hList.enqueue(new HourlyCustomer(input1, input2));
empList.addItems(hList);
System.out.println("\n"+(input2 + " " + input1) + " is successful queued");
System.out.println("\nDo you still want to enqueue?<1> or do you want to view all in queue?<0> or \nBack to main menu for dequeueing?<menu>: ");
choice = sc.nextInt();
}while (choice != 0);
System.out.println("\nThe customers' names are: \n");
while (empList.hasItems()) {
Customer emp = empList.dequeue();
System.out.println(emp.firstName + " " + emp.lastName + "\n" );
}
// int choose;
// do{
//
//
// System.out.println("\nGo back to main?<1=Yes/0=No>: \n");
// choose = sc.nextInt();
// }while (choose != 1);
break;
case 2:
if (empList.isEmpty()) {
System.out.println("The queue is empty!");
}
else{
System.out.println("\nDequeued customer: " +empList.getFirst());
empList.removeFirst();
System.out.println("\nNext customer in queue: " +empList.getFirst()+"\n");
}
break;
case 0:
System.exit(0);
default:
System.out.println("Invalid choice");
}
}
catch(InputMismatchException e){
System.out.println("Please enter 1-5, 0 to quit");
sc.nextLine();
}
}while(choice != 0);
}
}
}
Case 2 shows no error but when I run it on the IDE it shows:
Exception in thread "main" java.util.NoSuchElementException at
java.util.LinkedList.getFirst(Unknown Source) at
GenQueue.getFirst(something.java:44) at
something.main(something.java:113)
Any idea why this happen? and how to fix it? Your help will be very much appreciated, from python I just went Java today, newbie here.
NoSuchElementException is thrown by LinkedList.getFirst when the list is empty.
You should handle that particular case before calling that method, for example:
if (!empList.hasItems()) {
System.out.println("The queue is empty!");
} else {
System.out.println("First in queue: " +empList.getFirst());
... // rest of code
}
I have this code, that I'm trying to take the user input from the addEntry() method and write a method to save that to file.
public class GradeBook {
private String course;
private ArrayList<Person> students = new ArrayList<Person>();
private ArrayList<GradeBookEntry> entries = new ArrayList<GradeBookEntry>();
public GradeBook(String course){
this.course = course;
}
public String getCourse() {
return course;
}
public void setCourse(String course) {
this.course = course;
}
public void addStudent( Person student ){
students.add(student);
}
public void addEntry(){
System.out.println("Grade which student: ");
for (int i = 0; i < students.size(); i++) {
System.out.println(i + " " + students.get(i).getName());
}
Scanner reader = new Scanner(System.in);
int studentIndex = reader.nextInt();
reader.nextLine();
System.out.println("Enter the assessment name: ");
String assessmentName = reader.nextLine();
System.out.println("Homework (1) or exam (2): ");
int entryType = reader.nextInt();
reader.nextLine();
GradeBookEntry newEntry;
// TODO: create either a Homework or Exam entry
if( entryType == 1 ){
newEntry = new HomeworkEntry(assessmentName);
}
else {
newEntry = new ExamEntry(assessmentName);
}
// TODO: add getData method to the Homework and Exam
newEntry.getData();
newEntry.setStudent(students.get(studentIndex));
entries.add(newEntry);
}
This is the method below that I created but the text file doesnt have the correct data in it, I guess I somehow need the variables from the first method like "studentIndex" "entryType" etc., can you point me in the right direction?
public void writeFile(String fileName){
try {
FileWriter writer = new FileWriter(fileName);
for (int i=0; i<entries.size(); i++){
writer.write(students.get(i).toString());
}
writer.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
Overriding toString of Person class should be the correct way to go about this.
So, when I run this, I get no exceptions, but the execution halts. I entered a few lines of code to see where the hault is coming from. On initial execution, it creates a file in the path given in the Customer class. Once I do one of the actions, it doesn't let me go past the first debugging line. Ideas?
Heres the application:
package javaapplication18.pkg3;
import java.util.ArrayList;
import java.util.Scanner;
public class JavaApplication183 {
/**
* #param args the command line arguments
*/
static boolean keepGoing = true;
public static void main(String[] args) {
System.out.println("Welcome to the Customer Maintenance application");
//keepGoing = true;
Scanner sc = new Scanner(System.in);
while (keepGoing){
displayMenu();
String userChoice = getRequiredString("Enter a command: ", sc);
System.out.println("DEBUG LINE 1");
CustomerTextFile textFile = new CustomerTextFile();
System.out.println("DEBUG LINE 2");
performAction(userChoice, textFile);
System.out.println("DEBUG LINE 3");
}
// TODO code application logic here
}
public static void displayMenu() {
System.out.println();
System.out.println("COMMAND MENU");
System.out.println("list - List all customers");
System.out.println("add - Add a customer");
System.out.println("del - Delete a customer");
System.out.println("help - Show this menu");
System.out.println("exit - Exit this application");
System.out.println();
}
public static void performAction(String choice, CustomerTextFile textFile){
Scanner sc = new Scanner(System.in);
switch (choice.toLowerCase()) {
case "list":
//action
ArrayList<Customer> currentList = textFile.getCustomers();
for (Customer c : currentList) {
System.out.print(c.getEmail() + "\t");
System.out.print(c.getFirstName() + "\t");
System.out.println(c.getLastName());
}
break;
case "add":
String email = getRequiredString("Enter customer email address:", sc);
String firstName = getRequiredString("Enter first name:", sc);
String lastName = getRequiredString("Enter last name:", sc);
Customer c = new Customer(email, firstName, lastName);
textFile.addCustomer(c);
System.out.println(firstName + lastName + " was added to the database.");
break;
case "del":
String deleteUserByEmail = getRequiredString("Enter customer email to delete:", sc);
Customer delCustomer = textFile.getCustomer(deleteUserByEmail);
textFile.deleteCustomer(delCustomer);
break;
case "help":
//displayMenu();
break;
case "exit":
keepGoing = false;//exit();
break;
default:
System.out.println("You entereed something not in the list. Please try again.");
System.out.println();
}
}
public static boolean exit(){
System.out.println("Exit");
return false;
}
public static String getRequiredString(String prompt, Scanner sc) {
String s = "";
boolean isValid = false;
while (isValid == false) {
System.out.print(prompt);
s = sc.nextLine();
if (s.equals(""))
System.out.println("Error! This entry is required. Try again.");
else
isValid = true;
}
return s;
}
}
Here is the CustomerTextFile class:
package javaapplication18.pkg3;
import java.io.*;
import java.nio.file.*;
import java.util.ArrayList;
public class CustomerTextFile implements CustomerDAO{
private ArrayList<Customer> customers = null;
private Path customersPath = null;
private File customersFile = null;
public CustomerTextFile(){
customersPath = Paths.get("customers.txt");
customersFile = customersPath.toFile();
customers = this.getCustomers();
}
#Override
public Customer getCustomer(String emailAddress) {
for (Customer c : customers) {
if (c.getEmail().equals(emailAddress))
return c;
}
return null;
//throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates.
}
#Override
public ArrayList<Customer> getCustomers() {
if (customers != null)
return customers;
customers = new ArrayList<>();
if (!Files.exists(customersPath)) {
try {
Files.createFile(customersPath);
}
catch (IOException e) {
return null;
}
}
if (Files.exists(customersPath)) {
try (BufferedReader in = new BufferedReader(new FileReader(customersFile))){
String line = in.readLine();
while(line != null) {
String[] columns = line.split("\t");
String email = columns[0];
String firstName = columns[1];
String lastName = columns[2];
Customer c = new Customer(email, firstName, lastName);
customers.add(c);
}
}
catch (IOException e) {
System.out.println(e);
return null;
}
}
return customers;
}
#Override
public boolean addCustomer(Customer c) {
customers.add(c);
return this.saveCustomers();
//throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates.
}
#Override
public boolean updateCustomer(Customer c) {
Customer oldCustomer = this.getCustomer(c.getEmail());
int i = customers.indexOf(oldCustomer);
customers.remove(i);
customers.add(i, c);
return this.saveCustomers();
//throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates.
}
#Override
public boolean deleteCustomer(Customer c) {
customers.remove(c);
return this.saveCustomers();
}
private boolean saveCustomers() {
try (PrintWriter out = new PrintWriter(new BufferedWriter(new FileWriter(customersFile)))){
for (Customer customer : customers) {
out.print(customer.getEmail() + "\t");
out.print(customer.getFirstName() + "\t");
out.println(customer.getLastName());
}
out.close();
return true;
}
catch (IOException e) {
return false;
}
}
}
Im not certain if the problem is in the application or if it is in the textfile class
run:
Welcome to the Customer Maintenance application
COMMAND MENU
list - List all customers
add - Add a customer
del - Delete a customer
help - Show this menu
exit - Exit this application
list
DEBUG LINE 1
Above was an example of the console output.
Why are you declaring a string inside the loop?
try this instead:
Scanner sc = new Scanner(System.in);
String userChoice;
do {
displayMenu();
userChoice = sc.nextLine(); //takes in the entire lien you type in
System.out.println("DEBUG LINE 1");
CustomerTextFile textFile = new CustomerTextFile();
System.out.println("DEBUG LINE 2");
performAction(userChoice, textFile);
System.out.println("DEBUG LINE 3");
} while(keepGoing);
Hope this helps
The following code is two methods, one for saving to a file using object serialization and one for loading and deserializing the saved file for the user to read:
private void SaveDeck() throws Exception {
ObjectOutputStream oos = null;
FileOutputStream fout = null;
try{
fout = new FileOutputStream(filePath, true);
oos = new ObjectOutputStream(fout);
oos.writeObject(theDeck);
} catch (Exception ex) {
ex.printStackTrace();
}finally {
if(oos != null){
oos.close();
}
}
}
private FlashCardDeck[] loadDeck(){
user.setDeckMade(true);
try {
FileInputStream fis = new FileInputStream(filePath);
ObjectInputStream in = new ObjectInputStream(fis);
this.theDeck = (FlashCardDeck[])in.readObject();
in.close();
}
catch (Exception e) {
System.out.println(e);
}
return theDeck;
}
The error I'm getting is on the load method:
java.io.WriteAbortedException: writing aborted; java.io.NotSerializableException: myPackage.UserInterface
Saving works fine; I've opened up the .ser file after the SaveDeck method has executed and everything seemed to check out properly.
My question is if the problem is with the file itself, the save method, or external methods? I have made sure that everything not serializable (Namely, the Scanner class) is transient.
package myPackage.FlashCards;
import java.io.Serializable;
public class FlashCardDeck implements Serializable{
private static final long serialVersionUID = -1176413113990886560L;
public FlashCard[] theDeck;
public String deckName;
public FlashCardDeck(int cards, String name) {
this.deckName = name;
theDeck = new FlashCard[cards];
for (int i = 0; i < theDeck.length; i++) {
theDeck[i] = new FlashCard(i);
}
}
public String getQuestion(int i) {
return theDeck[i].QuestionToString();
}
public String getAnswer(int i ) {
return theDeck[i].AnswerToString();
}
public String getName() {
return deckName;
}
public int getDeckSize() {
return theDeck.length;
}
}
package myPackage.FlashCards;
import java.io.Serializable;
import java.util.Scanner;
public class FlashCard implements Serializable{
private static final long serialVersionUID = -8880816241107858648L;
private transient Scanner in = new Scanner(System.in);
String question;
String answer;
public FlashCard(int i) {
setCard(i);
}
public void setCard(int cards) {
System.out.println("What is the question for number " + (cards + 1) + "?");
question = in.nextLine();
System.out.println("What is the answer for number " + (cards + 1) + "?");
answer = in.nextLine();
}
public String QuestionToString() {
return "Question: " + question;
}
public String AnswerToString() {
return "Answer: " + answer;
}
}
package myPackage.FlashCards;
import java.io.Serializable;
import java.util.InputMismatchException;
import java.util.Scanner;
public class UserInterface implements Serializable{
private static final long serialVersionUID = 7755668511730129821L;
private int moreThanOnce = 0;
boolean deckMade = false;
private transient Scanner in = new Scanner(System.in);
public int AmountOfDecks() {
int decks;
System.out.println("How many decks will you be creating? (Type the number,
not the word. Ex: 2)");
decks = in.nextInt();
while (decks <= 0) {
System.out.println("You can't have less than one deck! Try again.");
decks = in.nextInt();
}
return decks;
}
public int StartMenu() {
int choice = 0;
moreThanOnce++;
if (moreThanOnce > 1) {
choice = SecondMenu();
} else {
System.out.println("\nFlash Card Creation Engine Ver. 2.5 ALPHA");
System.out.println("Press the cooresponding number for your
choice.");
System.out.println("1. Make a deck of flash cards");
System.out.println("2. Play flash cards");
System.out.println("3. Quit \n");
try { choice = in.nextInt(); } catch (InputMismatchException ime) {}
}
return choice;
}
public int AmountOfCards(int cards) {
int catchMe;
deckMade = true;
System.out.println("How many cards would you like? (Type the number, not the
word. Ex: 2)");
try {
catchMe = in.nextInt();
while (catchMe <= 0) {
System.out.println("You can't have less than one card! Try
again!");
catchMe = in.nextInt();
}
} catch (Exception ime) {
System.out.println("Uh-oh, you did that wrong! Let's try that again.
Try typing: 3");
cards = 0;
catchMe = in.nextInt();
}
cards = catchMe;
return cards;
}
public boolean getDeckMade() {
return deckMade;
}
public void setDeckMade(boolean makeDeckMade) {
this.deckMade = makeDeckMade;
}
public String NameOfDeck() {
String name;
System.out.println("What would you like to name this deck?");
name = in.next();
return name;
}
private int SecondMenu() {
int choice = 0;
System.out.println("Now what would you like to do?");
if (deckMade) {
System.out.println("1. Make or load a deck of flash cards -- DONE");
} else {
System.out.println("1. Make a deck of flash cards.");
}
System.out.println("2. Play flash cards");
System.out.println("3. Quit \n");
try { choice = in.nextInt(); } catch (InputMismatchException ime) {}
return choice;
}
public boolean SetMode() {
boolean timed = false;
int userChoice = 0;
while (userChoice < 1 || userChoice > 2) {
System.out.println("What mode are you selecting?");
System.out.println("1. Timed");
System.out.println("2. Normal");
System.out.println("3. Help");
System.out.println("4. Quit");
userChoice = in.nextInt();
if (userChoice == 1) {
timed = true;
} else if (userChoice == 3) {
System.out.println("Timed: Answers to a flash card will
appear after a set amount of seconds, then show the next
question after the same amount of seconds, which are set by
the user (that's you!)");
System.out.println("Normal: Answers to a flash card will
appear when the user (also you!) presses enter, and wait for
enter to be pressed before showing the next question.");
} else if (userChoice == 4) {
System.out.println("Have a good day.");
System.exit(0);
} else {
System.out.println("Choose from the proivded list -- 1 for
Timed mode, 2 for Normal mode, 3 to show the Help menu, 4 to
quit.");
System.out.println();
}
}
return timed;
}
public String setQuestion(int cards) {
String question = "";
return question;
}
public String setAnswer(int cards) {
String answer = "";
return answer;
}
}
The class you're trying to serialize (and any non-transient objects referenced by that class) must implement the Serializable interface.
judging by the error you have a UserInterface class referenced there which is not serializable.
Edit:
Also
new FileOutputStream(filePath, true);
always appends to the end of the file instead of clearing the file. You may have older data in the file that is not deserialized correctly. You could try removing the file and trying again.
In general - appending different objects to a file may be a bad choice considering data corruption. If different files for each deck are not an option, I might go for a separate DeckStore object that holds all the decks and gets serialized as a whole.
Class that you want to serialize should implement Serializable interface
public class FlashCardDeck implements Serializable {
// Fields and methods of the class ...
}
The serialization interface has no methods or fields and serves only to identify the semantics of being serializable.
i have created string arraylist in which i copied all the data from database. Then i removed one record from arraylist by using al.remove(1, null). Now i want to add record in the position on which there is no data. I mean i want to add data at the position where data is null. I did write al.set(position, "new") but its giving me run time error i.e. OutOfMemory. Pls help me. Thanks
import java.io.*;
import java.util.*;
public class DAOImpl implements DAO
{
String xs[];
List<String> al= new ArrayList<String>();
int value;
public void list()
{
try
{
BufferedReader br=new BufferedReader(new FileReader("insurance.db"));
String next;
while((next=br.readLine())!=null)
{
//System.out.println(next);
al.add(next);
}
for(int i=0;i<al.size();i++)
{
System.out.print(i+1+"] ");
String ar[]=(al.get(i)).split(":");
for(int q=0;q<3;q++)
{
System.out.print(ar[q]);
System.out.print(" ");
}
//System.out.println(al.get(i));
System.out.println("");
}
}
catch (FileNotFoundException ex)
{
ex.printStackTrace();
}
catch (IOException ex)
{
ex.printStackTrace();
}
}
public String[] readRecord(int recNo)
{
String stream=(al.get(x-1));
xs=stream.split(":");
return xs;
}
public void deleteRecord(int recNo)
{
int del=recNo;
al.set(del-1, null);
for(int i=0;i<al.size();i++)
{
if((al.get(i))==null)
{
continue;
}
else
{
System.out.print(i+1+"] ");
String ar[]=(al.get(i)).split(":");
for(int q=0;q<3;q++)
{
System.out.print(ar[q]);
System.out.print(" ");
}
System.out.println("");
}
}
}
public int addRecord()
{
for(int y=0;y<al.size();y++)
{
if((al.get(y))==null)
{
value=y+1;
}
if((al.get(y))==null)
{
al.add(y, "new");//m getting error here...
}
}
for(int i=0;i<al.size();i++)
{
if((al.get(i))==null)
{
continue;
}
else
{
System.out.print(i+1+"] ");
String ar[]=(al.get(i)).split(":");
for(int q=0;q<3;q++)
{
System.out.print(ar[q]);
System.out.print(" ");
}
System.out.println("");
}
}
return value;
}
}
and main method is as follow:
import java.io.*;
public class InsuranceMain
{
public static void main(String args[])throws Exception
{
BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
DAOImpl d=new DAOImpl();
d.list();
//deleterecord
System.out.println("Enter Record Number to delete record:");
int delete=Integer.parseInt(br.readLine());
d.deleteRecord(delete);
//addrecord
d.addRecord();//m getting error here
//readRecord
System.out.println("Enter Record Number:");
int s=Integer.parseInt(br.readLine());
String as[]=d.readRecord(s);
for(int v=0;v<as.length;v++)
{
System.out.println(as[v]);
}
}
}
short answer:
change this line:
al.add(y, "new");//m getting error here...
into
al.set(y, "new");
Reason:
if you al.add(y,"new"), then, all elements after y (inclusive) will be shifted right. So next time you meet the null again (y+1), you add another "new", do this loop no ending.
also it is not good if you changing the list's size within a for loop like this.