Serialization difficulty - java
I have had a good look in books and the internet but cannot find a solution to my specific problem.Im really worried as time is running out.
I am writing code for an account. Each transaction, if it is add or withdraw is an object. Information such as the add amount, withdraw amount, transaction number,balance and total spending in a particular category is an object. Each object is stored in an arrayList. There is also code for logging in because this will eventually be an app. It requires the user to input their student number(last 4 digits).
The code runs ok and it serializes on termination. Upon running the code i can see it has de serialized the file as there is a list of objects in the arrayList printed.
My problem is that the values such as student number and balance are 0 when the code runs.Also the transaction number does not increment. It does increment while the code runs but stops upon termination, starting at 1 when the code is run again.
I expected all values to be the same when de serailized as those in the last object in the arrayList before serialization.
I dont expect anyone to post the answer but if someone could point me in the right direction i could try to work it out myself.
Best regards
Richard
PS. transaction number is the first in the object, balance in the middle and student number the four digits at the end. I have added the main class and serialization class, if anyone wants to see the login, transaction or other classes i can post these too.
`
/**
* Created by Richard on 16/07/2014.
*/
public class AccountTest implements Serializable {
public static Scanner keyboard = new Scanner(System.in);
//Declare an ArrayList called 'transactions' which will hold instances of AccountInfo.
public static ArrayList transactions = new ArrayList<AccountInfo>();
//Declare and initiate variables relating to the AccountTest class.
private static int transactionNum = 0;
private static double depositAmount = 0;
public static double withdrawAmount = 0;
private static double currentBalance = 0;
// A method which prompts the user to either withdraw, add funds or quit,
//this method also updates the balance and transaction number.
public static void addOrSpend() {
do {//A do while loop to ensure that the method repeatedly asks the user for input.
System.out.println("Enter a 1 to deposit, 2 to withdraw, 3 to terminate:");
int choice = keyboard.nextInt();
if (choice == 1) {//The deposit choice that also sets transaction no. and the balance.
System.out.println("Enter an amount to deposit ");
depositAmount = keyboard.nextInt();
transactionNum = transactionNum + 1;
withdrawAmount = 0;
currentBalance = currentBalance + depositAmount;
//System.out.println("You entered: " + depositAmount);
}//if
if (choice == 2) {//The withdraw choice that also sets transaction num, balance and calls chooseCategory method.
System.out.println("Enter an amount to withdraw ");
withdrawAmount = keyboard.nextInt();
transactionNum = transactionNum + 1;
depositAmount = 0;
currentBalance = currentBalance - withdrawAmount;
AccountCategory.chooseCategory();
}//if
if (choice == 3) {//User option to quit the program.
AccountSerialize.serialize();
System.out.println("App terminated...");
System.exit(1);
}//if
AccountInfo acc = new AccountInfo();//creates an object of the AccountInfo class
//Setters for the various methods in the AccountInfo class,
// these initiate variables for instances of the class.
acc.setTransactionNum(transactionNum);
acc.setDepositAmount(depositAmount);
acc.setWithdrawAmount(withdrawAmount);
acc.setCurrentBalance(currentBalance);
acc.setAccommodation(AccountCategory.accommodation);
acc.setTransport(AccountCategory.transport);
acc.setUtilities(AccountCategory.utilities);
acc.setEntertainment(AccountCategory.entertainment);
acc.setEssentials(AccountCategory.essentials);
acc.setStudentNo(AccountLogin.studentNo);
transactions.add(acc);//Adds each new 'acc' object to the ArrayList 'transaction'.
//System.out.println("List:" + transactions);Unused print statement which shows contents of ArrayList for testing.
Formatter x = new Formatter();//Series of formatted print statements which allow the information to be displayed in tabular format with headings.
System.out.println(String.format("%-20s %-20s %-20s %-20s ", "Transaction No.", "Deposit amount", "Withdraw amount", "Current balance"));
System.out.println(String.format("%-20s %-20s %-20s %-20s", transactionNum, depositAmount, withdrawAmount, currentBalance));
System.out.println(String.format("%-20s %-20s %-20s %-20s %-20s ", "Accommodation", "Transport", "Utilities", "Entertainment", "Essentials"));
System.out.println(String.format("%-20s %-20s %-20s %-20s %-20s", AccountCategory.accommodation, AccountCategory.transport, AccountCategory.utilities,
AccountCategory.entertainment, AccountCategory.essentials));
} while (transactions.size() >= 0);//End of do while statement that repeatedly prompts the user.
}
//Main method from where the program starts and user logs in. Starts with request for user to login.
// This then allows the user to continue with the program.
public static void main(String args[]) {
AccountSerialize.deSerialize();
System.out.println("Testing to see if student num is saved, login is..." +AccountLogin.studentNo );
System.out.println("Testing to see if balance is saved, balance is..." +currentBalance );
if (AccountLogin.studentNo == 0)
{
AccountLogin.numberSave();
}
else
{
AccountLogin.login();
}
}//main
}//class AccountTest
import java.io.*;
import java.util.ArrayList;
import java.util.List;
/**
* Created by Richard on 24/07/2014.
*/
public class AccountSerialize {
public static String filename = "budgetApp.bin";
public static String tmp;
public static void serialize() {
try {
FileOutputStream fos = new FileOutputStream("budgetApp.bin");
ObjectOutputStream oos = new ObjectOutputStream(fos);
oos.writeObject(AccountTest.transactions);
oos.close();
fos.close();
} catch (IOException ioe) {
ioe.printStackTrace();
}
System.out.println("Done writing");
}//serialize()
public static void deSerialize(){
try
{
FileInputStream fis = new FileInputStream("budgetApp.bin");
ObjectInputStream ois = new ObjectInputStream(fis);
AccountTest.transactions = (ArrayList) ois.readObject();
ois.close();
fis.close();
}catch(IOException ioe){
ioe.printStackTrace();
return;
}catch(ClassNotFoundException c){
System.out.println("Class not found");
c.printStackTrace();
return;
}
for( Object tmp:AccountTest.transactions){
System.out.println(tmp);
}
}//deSerialize()
}//class
import java.util.Scanner;
/**
* Created by Richard on 22/07/2014.
*/
public class AccountCategory {
static Scanner keyboard = new Scanner(System.in);
//Declare and initiate variable to be used in this class.
public static double accommodation = 0;
public static double transport = 0;
public static double utilities = 0;
public static double entertainment = 0;
public static double essentials = 0;
//A method which prints a set of spending category choices and asks the user to choose.
//Also updates each category variable with the total amount spent in that category
public static void chooseCategory() {
System.out.println("Please choose a category of spending, enter corresponding number");
System.out.println("1:\tAccommodation \n2:\tTransport \n3:\tUtilities \n4:\tEntertainment " +
"\n5:\tEssentials ");
double choice = keyboard.nextInt();//User input.
if (choice == 1) {
accommodation = accommodation + AccountTest.withdrawAmount;
}//if
if (choice == 2) {
transport = transport + AccountTest.withdrawAmount;
}//if
if (choice == 3) {
utilities = utilities + AccountTest.withdrawAmount;
}//if
if (choice == 4) {
entertainment = entertainment + AccountTest.withdrawAmount;
}//if
if (choice == 5) {
essentials = essentials + AccountTest.withdrawAmount;
}//if
}//chooseCategory
}//Class AccountCategory
import java.io.Serializable;
import java.util.Scanner;
/**
* Created by Richard on 16/07/2014.
*/
public class AccountInfo implements Serializable {
//Declare variables for types of transaction, balance and categories of spending.
public int studentNo;
public int transactionNum;
public double depositAmount;
public double withdrawAmount;
public double currentBalance;
public double accommodation;
public double transport;
public double utilities;
public double entertainment;
public double essentials;
//Series of mutator methods which take and validate the user input from the Test class, setting new variable values
//for objects of this AccountInfo class.
public void setStudentNo(int studentNo) {
this.studentNo = studentNo;
}
public void setTransactionNum(int transactionNum) {
this.transactionNum = transactionNum;
}
public void setDepositAmount(double depositAmount) {
this.depositAmount = depositAmount;
}
public void setWithdrawAmount(double withdrawAmount) {
this.withdrawAmount = withdrawAmount;
}
public void setCurrentBalance(double currentBalance) {
this.currentBalance = currentBalance;
}
public void setAccommodation(double accommodation) {
this.accommodation = accommodation;
}
public void setTransport(double transport) {
this.transport = transport;
}
public void setUtilities(double utilities) {
this.utilities = utilities;
}
public void setEntertainment(double entertainment) {
this.entertainment = entertainment;
}
public void setEssentials(double essentials) {
this.essentials = essentials;
}
//A toString method to ensure printed information is user readable
public String toString() {
return "AccountInfo[" + transactionNum + "," + depositAmount + "," + withdrawAmount + "," + currentBalance + "," +
accommodation + "," + transport + "," + utilities + "," + entertainment + "," + essentials + ","+studentNo+"]";
}//toString
}//class AccountInfo
import java.util.InputMismatchException;
import java.util.Scanner;
/**
* Created by Richard on 20/07/2014.
*/
public class AccountLogin {
public static Scanner keyboard = new Scanner(System.in);
//Declare and initiate variables.
public static int studentNo=0;
public static int login=0;
public static void login() {
if (studentNo > 0 && Integer.toString(studentNo).length() == 4)//Validation test.
{
System.out.println("Log in with last four digits of your student number:");
login = keyboard.nextInt();//User input.
}//if
if(login==studentNo){
AccountTest.addOrSpend();//If validated
}//if
else{
enterNoAgain();
}//else
}//login()
//This method checks to see if the user has already entered and saved their details, if not the user is prompted to do so.
//If the user has already entered their details
public static void numberSave() {
if (studentNo == 0) {//Checks to see if student number has already been entered.
System.out.println("Enter and save the last four digits of your student number, use this to login to the Budgeting app:");
studentNo = keyboard.nextInt();//User input.
if (studentNo > 0 && Integer.toString(studentNo).length() == 4) {//Checks that user input meets requirements.
System.out.println("You are now logged in:");
AccountTest.addOrSpend();//Program starts at this point once user input is validated.
}//if
else {//If user input does not meet criteria, the following method is called.
enterNoAgain();
}//else
}//if
}//numberSave()
// This method takes over if the user has not input valid data.
// The user is instructed to do so and is given a further 2 opportunities before the program exits
public static void enterNoAgain() {
System.out.println("Invalid input: Use 4 numbers only, try again");//Prompt.
studentNo = keyboard.nextInt();//User input.
if (studentNo > 0 && Integer.toString(studentNo).length() == 4) {//Validation test.
AccountTest.addOrSpend();//If validated
}//if
else {
System.out.println("Last attempt, input last four digits of your student number");//Prompt.
studentNo = keyboard.nextInt();//User input.
if (studentNo > 0 && Integer.toString(studentNo).length() == 4) {//Validation test.
AccountTest.addOrSpend();//If validated
}//if
else {
AccountSerialize.serialize();//Save to file
System.out.println("You failed to login");
System.out.println("App terminated...");
System.exit(1);//Program exits due to invalid user input.
}//else
}//else
}//enterNoAgain()
}//class AccountLogin
`
AccountTest
AccountInfo[1,1000.0,0.0,1000.0,0.0,0.0,0.0,0.0,0.0,1234]
AccountInfo[1,1000.0,0.0,1000.0,0.0,0.0,0.0,0.0,0.0,1234]
AccountInfo[1,50.0,0.0,50.0,0.0,0.0,0.0,0.0,0.0,3333]
AccountInfo[1,50.0,0.0,50.0,0.0,0.0,0.0,0.0,0.0,1234]
AccountInfo[1,1000.0,0.0,1000.0,0.0,0.0,0.0,0.0,0.0,1234]
AccountInfo[1,1000.0,0.0,1000.0,0.0,0.0,0.0,0.0,0.0,6666]
AccountInfo[1,1000.0,0.0,1000.0,0.0,0.0,0.0,0.0,0.0,1234]
AccountInfo[2,0.0,50.0,950.0,50.0,0.0,0.0,0.0,0.0,1234]
AccountInfo[1,1000.0,0.0,1000.0,0.0,0.0,0.0,0.0,0.0,1234]
AccountInfo[1,500.0,0.0,500.0,0.0,0.0,0.0,0.0,0.0,1234]
AccountInfo[1,1000.0,0.0,1000.0,0.0,0.0,0.0,0.0,0.0,1234]
AccountInfo[2,0.0,50.0,950.0,0.0,0.0,50.0,0.0,0.0,1234]
AccountInfo[1,1000.0,0.0,1000.0,0.0,0.0,0.0,0.0,0.0,1234]
AccountInfo[2,0.0,50.0,950.0,50.0,0.0,0.0,0.0,0.0,1234]
Testing to see if student num is saved, login is...0
Testing to see if balance is saved, balance is...0.0
Enter and save the last four digits of your student number, use this to login to the Budgeting app:
1234
You are now logged in:
Enter a 1 to deposit, 2 to withdraw, 3 to terminate:
1
Enter an amount to deposit
1000
Transaction No. Deposit amount Withdraw amount Current balance
1 1000.0 0.0 1000.0
Accommodation Transport Utilities Entertainment Essentials
0.0 0.0 0.0 0.0 0.0
Enter a 1 to deposit, 2 to withdraw, 3 to terminate:
2
Enter an amount to withdraw
50
Please choose a category of spending, enter corresponding number
1: Accommodation
2: Transport
3: Utilities
4: Entertainment
5: Essentials
1
Transaction No. Deposit amount Withdraw amount Current balance
2 0.0 50.0 950.0
Accommodation Transport Utilities Entertainment Essentials
50.0 0.0 0.0 0.0 0.0
Enter a 1 to deposit, 2 to withdraw, 3 to terminate:
3
Done writing
App terminated...
Process finished with exit code 1
Related
scanner nextLine() skip and failed read
Not actually sure what's wrong, just that at line 81 my scan object is skipped and then the program continues with no clear attempt to read anything, thoughts on what's wrong? btw working in eclipse import java.util.*; public class Hospital { //--- Instance Variables private Patient patient; private Scanner scan; private double totalPrivateRoomCharges; private double totalSemiPrivateRoomCharges; private double totalWardRoomCharges; private double totalTelephoneCharges; private double totalTelevisionCharges; private double totalReceipts; //--- Constructors public Hospital() { scan = new Scanner(System.in); totalPrivateRoomCharges = 0; totalSemiPrivateRoomCharges = 0; totalWardRoomCharges = 0; totalTelephoneCharges = 0; totalTelevisionCharges = 0; totalReceipts = 0; mainMenu(); } //--- Methods public void mainMenu() { int ans = 0; do { System.out.println(" Community Hospital"); System.out.println(); System.out.println(" Main Menu"); System.out.println(); System.out.println("1) Enter Patient Billing Information"); System.out.println("2) Print Daily Summary Report"); System.out.println("3) Exit"); System.out.println(); System.out.print("Selection: "); ans = scan.nextInt(); System.out.println(); if(ans == 1) { patientBillingInfo(); } if(ans == 2) { printSummaryReport(); } } while(ans != 3); } // precondition: none // postcondition: displays a menu that allows the user to enter a patient's // billing info which includes the patient's name, the number of days the // patient stayed in the hospital, and the type of room // (private, semi-private, ward). // Once the patient info is retrieved a patient object is created and a // billing report is generated that includes the patient's name, length // of stay, and the charges incurred including the bill total. // The totals that are used to print the hospitals daily summary report // are updated. public void patientBillingInfo() { String name = ""; int days = 0; String room = ""; System.out.println(" Community Hospital"); System.out.println(); System.out.println(" Patient Billing Query"); System.out.println(); System.out.println("Enter Patient Name: "); here the scan object seems to be completely skipped and dose not read at all just moves to the next line and continues. name = scan.nextLine(); //getting skiped System.out.println("Enter number of days in Hospital: "); days = scan.nextInt(); System.out.println("Enter Room type(P, S, W): "); room = scan.next(); System.out.println(); System.out.println(); if(!((room.equalsIgnoreCase("P")) || (room.equalsIgnoreCase("S")) || (room.equalsIgnoreCase("W")))) { System.out.println("Incorect room information"); System.out.println("Please enter P, S, or W for room selection"); System.out.println(); patientBillingInfo(); } else { if(room.equalsIgnoreCase("P")) totalPrivateRoomCharges += 1*days; if(room.equalsIgnoreCase("S")) totalSemiPrivateRoomCharges += 1*days; if(room.equalsIgnoreCase("W")) totalWardRoomCharges += 1*days; totalTelephoneCharges += 1*days; totalTelevisionCharges += 1*days; patient = new Patient(name, days,room); } System.out.println(" Community Hospital"); System.out.println(); System.out.println(" Patient Billing Statement"); System.out.println(); System.out.println("Patient's name: " + patient.getName()); System.out.println("Number of days in Hospital: " + patient.getDays()); System.out.println(); System.out.println("Room charge $ " + patient.getRoomCharge()); System.out.println("Telephone charge $ " + patient.getTelephoneCharge()); System.out.println("Television charge $ " + patient.getTelevisionCharge()); System.out.println(); System.out.println("Total charge $ " +patient.getTotalCharge()); System.out.println(); System.out.println(); mainMenu(); } // precondition: none // postcondition: a summary report is printed that includes the daily total // room charges for each type of room, the daily total telephone charges, // and the daily total television charges. The report also includes the // total receipts for the day. public void printSummaryReport() { double tPRC = 225.0*totalPrivateRoomCharges; double tSPRC = 165.0*totalSemiPrivateRoomCharges; double tWRC = 95.0*totalWardRoomCharges; double tTpC = 1.75*totalTelephoneCharges; double tTvC = 3.50*totalTelevisionCharges; double tR = tPRC+tSPRC+tWRC+tTpC+tTvC; System.out.println(" Community Hospital"); System.out.println(); System.out.println(" Daily Billing Summary"); System.out.println(); System.out.println("Room Charges"); System.out.println(" Private: $" + tPRC); System.out.println(" Semi-Private: $" + tSPRC); System.out.println(" Ward: $" + tWRC); System.out.println("Telephone Charges: $" + tTpC); System.out.println("Telvision Charges: $" + tTvC); System.out.println(); System.out.println("Total Receipts: $" + tR); System.out.println(); } } edit: so it just occurred to me that maybe just maybe the rest of the code that this goes with might be useful dunno why I didn't think about this sooner but here's the rest the class that actually runs public class Administrator { public static void main(String[] args) { Hospital hospital = new Hospital(); } } and the class that works the patient info public class Patient { //--- Constants public final double PRIVATE = 225.00; public final double SEMI = 165.00; public final double WARD = 95.00; public final double TELEPHONE = 1.75; public final double TELEVISION = 3.50; //--- Instance Variables private String name; private String roomType; private int days; //--- Constructors public Patient(String n, int d, String rT) { name = n; days = d; roomType = rT; } //--- Methods // precondition: none // postcondition: returns the patient name public String getName() { return name; } // precondition: none // postcondition: returns the length of stay in days public int getDays() { return days; } // precondition: none // postcondition: returns the room type ("P", "S", "W") public String getRoomType() { return roomType; } // precondition: none // postcondition: returns the room charge which is dependant upon // the room type and the length of stay. public double getRoomCharge() { double charge = 0; if(getRoomType().equalsIgnoreCase("P")) charge = 225.00*getDays(); if(getRoomType().equalsIgnoreCase("S")) charge = 165.00*getDays(); if(getRoomType().equalsIgnoreCase("W")) charge = 95.00*getDays(); return charge; } // precondition: none // postcondition: returns the telephone charge which is dependant upon // the length of stay public double getTelephoneCharge() { double charge = 1.75*getDays(); return charge; } // precondition: none // postcondition: returns the television charge which is dependant upon // the length of stay public double getTelevisionCharge() { double charge = 3.50*getDays(); return charge; } // precondition: none // postcondition: returns the total charge which is the sum // of the room charge, telephone charge, and television charge. public double getTotalCharge() { double charge = getRoomCharge()*getTelephoneCharge()+getTelevisionCharge(); return charge; } } really don't know why it didn't occur to me sooner to do this but whatever live and lern right
You could simply scan a line and then parse it as the integer for Integer values. so for reading integers instead of val=scan.nextInt() you could use String strVal = scan.nextLine(); try { val = Integer.parseInt(strVal); } catch (NumberFormatException e) { //maybe try again, or break the code ... or proceed as you wish. } this is because the nextInt() does not take the "Enter" key into account, and when you press enter after the nextInt() the int is read into the variable expecting nextInt() and the "Return" Key is accepted by the nextLine() which results in an empty line being read into the variable.
In public void mainMenu() you need to add scan.nextLine(); after ans = scan.nextInt(); in order to clear the rest of the input buffer. ans = scan.nextInt(); scan.nextLine(); // <----- Add this line here
Why is my withdraw method allowing me to take out more then has been deposited?
I have to write a ATM program for my computer science class. It works for the most part, apart from a couple logic problems within the programs itself. So far, from what I can tell, my ATM will deposit the correct amount of money that I tell it to however, when I withdraw money, it does not always withdraw the correct amount if I purposefully make an error (such as trying to take out an amount that is not a multiple of 20). I am also running into an issue where if I try to take out more money then is actually in the account, it will become a negative value, which I do not want to be allowed. I want it not to subtract the value that causes it to become negative and for it to prompt the user until a value less then or equivalent to the balance is able to be taken out. I am rather new to coding so please excuse my rather messy code. My error is probably around the else if statement where option == 3. Here is my code: import java.io.*; import java.util.*; public class aTMLauncher { public static int options=0; public static void main(String [] args) { Scanner input = new Scanner(System.in); aTMTester atm = new aTMTester(); System.out.println("Login: \n(case sensitive)"); System.out.print("Username > "); String usernameInput=input.nextLine(); int count=4; while (!usernameInput.equals(aTMTester.getUsername())) { System.out.println("\nIncorrect input. Please try again. You have " + (count-1) + " trys remaining attempts."); System.out.println("Login: \n(case sensitive)"); System.out.print("Username > "); count--; if(count==0) { System.out.println("No remain attempts, system will now exit"); System.exit(0); } usernameInput = input.nextLine(); } System.out.print("Pin > "); int PINInput=input.nextInt(); int count1=4; while (PINInput<aTMTester.getPIN() || PINInput>aTMTester.getPIN()) { System.out.println("\nIncorrect input. Please try again. You have " + (count1-1) + " trys remaining"); System.out.print("Pin > "); count1--; PINInput=input.nextInt(); if(count1==0) { System.out.println("No remain attempts, system will now exit"); System.exit(0); } } System.out.println("\nWelcome, " + aTMTester.getUsername() +"!"); while(PINInput==2468) { atm.main(); options = input.nextInt(); if (options==4) { atm.logout(); } else if(options==2) { System.out.println("How much money would you like to deposit?"); System.out.print("$ "); atm.deposit = input.nextInt(); atm.balance+=atm.deposit; System.out.println("Your new balance is $" + atm.balance +"0"); } else if(options==3) { System.out.println("How much money will you be withdrawing? \n(Only amounts divisible by 20 are accepted) \n$"); atm.withdraw= input.nextInt(); atm.balance-=atm.withdraw; if(atm.withdraw%20==0.0) { System.out.println("You took out " +atm.withdraw); System.out.println("Your new balance is $" + atm.balance); } while(atm.withdraw%20>0) { System.out.println("Invalid withdraw amount. Please retry."); System.out.println("\nHow much money will you be withdrawing? \n(Only amounts divisible by 20 are accepted)"); atm.withdraw= input.nextInt(); System.out.println("You took out " +atm.withdraw); System.out.println("Your new balance is $" + atm.balance); } if(!(atm.balance>0.0)) { System.out.println("You are not allowed to take out more then you have in your account \n Please retry"); atm.withdraw= input.nextInt(); } } else if(options==1) { System.out.println("Your account balance is $"+atm.balance+"0"); } } } } public class aTMTester { private static final String username = "David"; private static final int PIN = 2468; public static int deposit, withdraw; public static double balance=0.00; private String menu; /* * Default constructor */ public aTMTester() { } public static String getUsername() { return username; } public static int getPIN() { return PIN; } public static void main() { System.out.println("\n+++++++++++Account: "+ username +"+++++++++++"); System.out.println("1. Check Account Balance"); System.out.println("2. Deposit Checks"); System.out.println("3. Withdraw Money"); System.out.println("4. Logout"); System.out.print("\nWhat would you like to do next?\n"); } public static void logout() { System.out.println("Thanks for usinging the David Vachlon Inc. ATM. We hope you expierence was fast and simple! Have a great day."); System.exit(0); } public static double getBalance() { return balance; } public static void deposit() { balance+=deposit; } public static void withdraw() { balance-=withdraw; } }
You should do atm.balance -= atm.withdraw; after all checks was successfully passed. For instance, you may restructure your code as follows: boolean ok = false; while (!ok) { System.out.println("\nHow much money will you be withdrawing? \n(Only amounts divisible by 20 are accepted)"); atm.withdraw = input.nextInt(); if (atm.withdraw % 20 != 0) { System.out.println("Invalid withdraw amount. Please retry."); } else if (atm.balance < atm.withdraw) { System.out.println("You are not allowed to take out more then you have in your account \n Please retry"); } else if (atm.withdraw < 0) { // Probably you should not allow to withdraw a negative amount of money } else { ok = true; } } atm.balance -= atm.withdraw; System.out.println("You took out " + atm.withdraw); System.out.println("Your new balance is $" + atm.balance);
How to perform arithmetic operation between the objects written in a file?
In my program, users enter values and those get stored in arrayList. ArryList objects are written into a file. I have used file-i/o, object-i/o stream for writing and readin in file.Now I want to perform addition and subtraction among the objects (int or double). That is withdrawing money from one account should be added with another account, and their value must be subtracted and added with the particular acount's amount. And finally I want that value must be updated so that it can print out and show the current status. How could I do that? This is the main class: public class BankApp_Assignment { //static int numOfAcc = 0; public static void main(String[] args) { System.out.println("WELCOME TO OUR BANK!\n\n"); List<BankAccount> bankAccounts = new ArrayList<BankAccount>(); List<BankAccount> bankAccounts2 = new ArrayList<BankAccount>(); ReaderWriter rw=new ReaderWriter(); while (true) { System.out.println("Choose your option:\n" + "1. Create new account\n" + "2. Deposit/withdraw\n" + "3. View One account\n" + "4. Deleting an account\n" + "5. View all the accounts\n" + "6. Return to menu\n"); System.out.println("*************\n" + "************"); option1 = sc.nextInt(); sc.nextLine(); //switch-case starts switch (option1) { case 1: //create account BankAccount bankAcc = new BankAccount(); System.out.println("Enter Full Name:"); bankAcc.setName(sc.nextLine()); System.out.println("Choose an Account Number:"); bankAcc.setAccNum(sc.nextInt()); System.out.println("Choose the initial amount:"); bankAcc.setInitiateAmount(sc.nextDouble()); //adding those into the arrayList bankAccounts.add(bankAcc); rw.writeToFile(bankAccounts); System.out.println("-------------\n" + "-------------"); break; case 2: bankAccounts2=(List<BankAccount>)rw.readFromFile(); //First displaying the current accouns info System.out.println("Name \tAccount No \tInitial Amount"); for (BankAccount bankAccount : bankAccounts2) { System.out.println(bankAccount); } System.out.println("\t\t.........\n" + "\t\t........."); System.out.println("To transfer money within the bank accounts enter 1\n" + "To deposit/withdraw money in the same account enter 2"); option2 = sc.nextInt(); sc.nextLine(); //inner switch-case starts switch (option2) { case 1: /* BankAccount is the class for setter and getter bankAccounts2 is the arrayList for reading objects from file */ bankAccounts2 = (List<BankAccount>) rw.readFromFile(); BankAccount fromAcc = null; BankAccount toAcc = null; System.out.println("Enter the account number you want to withdraw from:"); withdraw_accNum = sc.nextInt(); System.out.println("Enter the amount you want to withdraw:"); withdraw_amount = sc.nextDouble(); System.out.println("Enter the account number you want to deposit to:"); deposit_accNum = sc.nextInt();//the deposit amount is alwyas the same as withdraw_amount //find the matching acc number:withdraw_accNum for (BankAccount listItemsFirst : bankAccounts2) { //if the withdraw acc num matches with the given one if (listItemsFirst.getAccNum() == withdraw_accNum) { //store it fromAcc = listItemsFirst; break; } } //find the matching acc number: deposit_accNum for (BankAccount listItemsSec : bankAccounts2) { //if the withdraw acc num matches with the given one if (listItemsSec.getAccNum() == deposit_accNum) { //store it toAcc = listItemsSec; break; } } //if the withdraw amount is bigger than the current balance if (withdraw_amount > fromAcc.getInitialAmount()) { System.out.println("Withdrawing Amount was bigger than the Initial amount.\nChoose the menu again. ."); break; } //subtracting and adding the withdrawn amount fromAcc.setInitiateAmount(fromAcc.getInitialAmount() - withdraw_amount); toAcc.setInitiateAmount(toAcc.getInitialAmount() + withdraw_amount); System.out.println("DONE!\t print them out to see the current status."); System.out.println(""); break; case 2://deposit/withdraw money in the same accounts bankAccounts2=(List<BankAccount>)rw.readFromFile(); BankAccount fromAcc_SameAcc = null; BankAccount toAcc_SameAcc = null; System.out.println("Enter the account number you want to deposit or withdraw from:"); //read the accNum depOrWithAccountNum = sc.nextInt(); System.out.println("Enter the amount (To withdraw enter a negative value)"); //read the amount depOrWithAmount = sc.nextDouble(); //checking the matching account number in arrayList for (BankAccount listItemsThird : bankAccounts2) { if (listItemsThird.getAccNum() == depOrWithAccountNum) { fromAcc_SameAcc = listItemsThird; break; } } if (depOrWithAmount - 1 < fromAcc_SameAcc.getInitialAmount()) { System.out.println("Withdraw amount is bigger than the current amount.\nChoose the menu again. ."); break; } if (depOrWithAmount < 0) {//the amount is negative fromAcc_SameAcc.setInitiateAmount(fromAcc_SameAcc.getInitialAmount() + depOrWithAmount); } else { fromAcc_SameAcc.setInitiateAmount(fromAcc_SameAcc.getInitialAmount() + depOrWithAmount); } break; } //inner switch-case ends System.out.println("\n\n"); break; case 3: //View One account bankAccounts2=(List<BankAccount>)rw.readFromFile(); BankAccount viewOneAccountNum = null; System.out.println("Enter the account number you want to see:"); viewOneAcc = sc.nextInt(); System.out.println("Name\tAccount No\tInitial Amount"); for (BankAccount viewOneAccountProperty : bankAccounts2) { if (viewOneAccountProperty.getAccNum() == viewOneAcc) { //viewOneAccountNum=viewOneAccountProperty; viewOneAccountNum = viewOneAccountProperty; System.out.println(viewOneAccountNum); } System.out.println(""); } break; case 4: bankAccounts2=(List<BankAccount>)rw.readFromFile(); //BankAccount AccToDel = null; //Deleting an account Iterator<BankAccount> it = bankAccounts2.iterator(); System.out.println("Enter the account you want to delete:"); deleteAcc = sc.nextInt(); while (it.hasNext()) { BankAccount next = it.next(); if (next.getAccNum() == deleteAcc) { it.remove(); } } rw.writeToFile(bankAccounts2); break; case 5: //View all the accounts/printing them out bankAccounts2=(List<BankAccount>)rw.readFromFile(); System.out.println("Name\tAccount No\tInitial Amount"); for (BankAccount bankAccount : bankAccounts2) { System.out.println(bankAccount); } System.out.println("\n\n"); break; case 6: //Quit return; } //switch-case ends } } } ReaderWriter: public class ReaderWriter{ public void writeToFile(List<BankAccount> accounts){ try { FileOutputStream fos=new FileOutputStream("C:\\Users\\Documents\\NetBeansProjects\\BankFile_assignment.txt"); ObjectOutputStream oos=new ObjectOutputStream(fos); oos.writeObject(accounts);//take the arrayList oos.flush(); oos.close(); fos.close(); } catch (Exception e) { e.printStackTrace(); } } public List<BankAccount> readFromFile(){ List<BankAccount>readData=null; try { FileInputStream fis=new FileInputStream("C:\\Users\Documents\\NetBeansProjects\\BankFile_assignment.txt"); ObjectInputStream ois=new ObjectInputStream(fis); //make an arrayList to get those object back //arrayList readData=(List<BankAccount>)ois.readObject(); ois.close(); fis.close(); } catch (Exception e) { e.printStackTrace(); } //return readData; return readData; } } BankAccount: package bankapp_assignment; import java.io.Serializable; public class BankAccount implements Serializable{ private String name; private int accNum; private double initiateAmount; //constructor public BankAccount() { this.name = null; this.accNum = 0; this.initiateAmount = 0; } public void setName(String name) { this.name = name; } public void setAccNum(int accNum) { this.accNum = accNum; } public String getName(String name){ return name; } public int getAccNum() { return accNum; } public void setInitiateAmount(double initiateAmount) { this.initiateAmount = initiateAmount; } public double getInitialAmount(){ return initiateAmount; } #Override public String toString() { return name + "\t\t" + accNum + "\t\t" + initiateAmount; } }
you should refactor whole main method. If I were you, I would use main only to lunch program, rest process in other methods. This way you would be able to use class fields all over program, and divide code into many methods. You should divide main beetween other methods, to at least method per action, exemple: case 1: createAccount(); break; (...) public void createAccount(){ code from your swich case 1 } etc. You can still use swich control, but should replece logic code to another method. When i run your code, input/output didn't work. Were you able to save/load file? I had to chage: File file = new File("//file path"); FileOutputStream fos = new FileOutputStream(file); ObjectOutput oos = new ObjectOutputStream(fos); Same with input. Then it worked. Now, we will try to deal with operation on BankAccounts from files. I change a little bit your code from case2/case2: deposit/withdraw, lets look at it: bankAccounts2 = rw.readFromFile(); // loading list from file BankAccount edited = new BankAccount(); // creating new object System.out.println("Enter the account number you want to deposit or withdraw from:"); double input = sc.nextInt(); // you don't need to create new variable every time you take input form user for(BankAccount account : bankAccounts2){ // every account in list if(account.getAccNum() == input) edited = account; // if acccNum match, give edited reference to chosen account } System.out.println("Enter the amount (To withdraw enter a negative value)"); input = sc.nextDouble(); double result = edited.getInitialAmount() + input; // result of operation if(result < 0){ // check if there is enough money on account System.out.println("Withdraw amount is bigger than the current amount.\nChoose the menu again. ."); break; }else{ edited.setInitiateAmount(result); // if there is, set new value } rw.writeToFile(bankAccounts2); // save file You can implement another operation in similar style. But still, you should consider dividing main into other methods, adding class fields, etc. EDIT: For question in comments. Because you use positive numbers for deposit, and negative numbers for withdraw, the operation on initialAmount will be always the same: initialAmount + input (if negative, is will subtract from amount), so you can treat it like an one case in your code. In your code you use this line twice: fromAcc_SameAcc.setInitiateAmount(fromAcc_SameAcc.getInitialAmount() + depOrWithAmount); so you already could merge both cases into one, to avoid unnecessary repetitions. So only case when action will differ, is when there is not enough money on a account, you check it by: if (depOrWithAmount - 1 < fromAcc_SameAcc.getInitialAmount()) but i think i will not work, because in withdraw operation depOrWithAmount is in negative numbers, so it will always be smaller than fromAcc_SameAcc.getInitialAmount(). You can use: if (depOrWithAmount < 1 - fromAcc_SameAcc.getInitialAmount()) (but i think it is not too readable) or: if (Math.abs(depOrWithAmount) > fromAcc_SameAcc.getInitialAmount()){} to compare absolute value of input with initialAmout. However i used: double result = edited.getInitialAmount() + input; if(result < 0){...} because it gives me result variable, which I can reuse if there is enough money, to gives new value to initialAmount. And if result is negative, it means that withdraw amount was bigger than initialAmount, so ther is no enough monay to withdraw. I hope you found something useful in my post.
Output user data to display class
package developer; import java.util.*; import java.lang.Math.*; public class Developer { static Scanner console = new Scanner(System.in); String workType; // This will be either an app, or game String name; int pay; int weekPay; int hrsWorked; double tax; public Developer() { name = "Ciaran"; } Developer(String appType, String coderName) { workType = appType; name = coderName; }// End developer Developer(String appType, int pay) // Class to choose the pay rate depending on if it is a game or app { System.out.println("Are you coding an app or a game? "); appType = console.next(); if(appType == "app") { pay = 20; } if(appType == "game") { pay = 30; } else { System.out.println("Please enter either 'app' or 'game' "); } }// End developer Developer(int hrsWorked, double tax, int weekPay, int pay) // Class to choose the tax bracket which the developer is in { System.out.println("Please enter how many hours you have worked this week: "); hrsWorked = console.nextInt(); weekPay = hrsWorked * pay; if(weekPay >= 865) { tax = 0.4; } else { tax = 0.21; } }// End developer Developer(int weekPay, int tax) // Gets the pay after tax { weekPay = weekPay * tax; }// End developer public void display() { System.out.println("This display method works"); System.out.println("User: " + name); } public static void main(String[] args) { Developer myDev = new Developer(); myDev.display(); } // End main }// End public class developer I am trying to get this program to ask the user what their name is; if they are developing a game or app and the amount of hours worked on it. With all this information I want to calculate how much the dev earns including tax. I cannot seem to get the display() method to ask the user the questions though and I have no idea what to do. I am hoping somebody out there can help me.
System.in will read input from the command line. You should wrap it with a java.util.Scanner and nextLine like this: Scanner scanner = new Scanner(System.in); String user_input = scanner.nextLine(); Be sure to check scanner.hasNextLine() before continuing or you'll get an error.
There are few things that could be done differently in your code, so let's break it down: 1.No need to make console static type, you can use: private Scanner console = new Scanner(System.in); 2.weekPay is of type int, but your tax is double, if you don't want weekPay to be cast to integer, change it to: double weekPay; 3.Later on, you are calculating weekPay after tax, so let's introduce a variable for that: double weekPayAfterTax; 4.All these Developer() methods are constructors, and I think you are slightly confused here. Of course, you can have many constructors, but for us, let's keep only the no-params constructor: public Developer() { name = "Ciaran"; //you could initialise all the other variables here as well, //I'll leave it as an exercise for you :) } 5.Let's create a method that will ask all the questions and set respective variables: void setData() { //let's get the name System.out.print("What's your name: "); name = console.nextLine(); System.out.print("Are you coding an app or a game? "); //since we want the user to enter 'app' or 'game' //we need to loop until we got these //we can do this by creating endless while loop, //which we will end when we have correct input while (true) { workType = console.next(); if (workType.equals("app")) { pay = 20.0; //stop the loop break; } else if (workType.equals("game")) { pay = 30.0; //stop the loop break; } else { System.out.print("Please enter either 'app' or 'game': "); //back to top } } //ok, we're out the loop, let's get number of hours System.out.print("Please enter how many hours you have worked this week: "); hrsWorked = console.nextInt(); //calculate weekPay weekPay = hrsWorked * pay; if(weekPay >= 865) { tax = 0.4; } else { tax = 0.21; } //calculate pay after tax weekPayAfterTax = weekPay - weekPay * tax; } 6.Let's update our display() method to show all the info: public void display() { System.out.println("This display method works"); System.out.println("User: " + name); System.out.println("Work type: " + workType); System.out.println("Pay: " + pay); System.out.println("Week pay: " + weekPay); System.out.println("Week pay after tax: " + weekPayAfterTax); } 7.In your main method, you can finally create an instance of Developer class and get the data: public static void main(String[] args) { Developer myDev = new Developer(); myDev.setData(); myDev.display(); } The code above can be improved (such as checking if user entered number where it's expected), and your problem can of course be done differently, but here's the start. Please check out some tutorials to learn the basics, such as this one, or this one. Most of all, experiment and don't let others put you down for not understanding something.
Reading user input in Java
I need to design and implement an application called CinemaPrice to determine how much a person pays to go the the cinema. The program should generate an age from 1 - 100 using the Random class and prompt the user for the full ticket price. Then display the appropriate ticket price using the currency format (an example in your book ). You may want to refer to the example we did together in class to help you with the "if statement". Decide ticket price on the following basis: 1. under 5, free; 2. aged 5 to 12, half price; 3. aged 13 to 54, full price; 4. aged 55, or over, free. I would really like some help on this I'm new to java and been spending hours on this now I would love to finish it :) This is what I have so far: import java.util.Scanner; //Needed for the Scanner class import java.util.Random; import java.text.DecimalFormat; public class CinemaPrice { public static void main(String[] args) //all the action happens here! { Scanner input = new Scanner (System.in); int age = 0; double priceNumber = 0.00; Random generator = new Random(); age = generator.nextInt(100) + 1; if ((age <= 5) || (age >=55) { priceNumber = 0.0; }else if (age <= 12){ priceNumber = 12.50; }else { system.out.println("Sorry, But the age supplied was invalid."); } if (priceNumber <= 0.0) { System.out.println("The person age " + age + " is free!); } else { System.out.println("Price for the person age " + age + "is: $" + priceNumber); } } //end of the main method } // end of the class I don't know how to prompt and read input from a user though - can you help?
The first issue that I see is that you need to update your conditional statement here as anything from 13 to 54 will be an invalid age... if ((age <= 5) || (age >=55) { priceNumber = 0.0; }else if (age <= 12){ priceNumber = 12.50; }else if (age < 55){ //whatever this ticket price is }else { system.out.println("Sorry, But the age supplied was invalid."); } Something like that would work...
You have stated that your real problem is getting data into your program, the following should demonstrate using the Scanner class public static void main(String[] args) { System.out.println("Enter an age"); Scanner scan=new Scanner(System.in); int age=scan.nextInt(); System.out.println("Your age was " + age); double price=scan.nextDouble(); System.out.println("Your price was " + price); } Now thats the basic idea, but if you provide an incorrect input (like a word) you can get an exception, you can however check that the input you're getting is correct and only accept it if its what you want, like this; public class Main{ public static void main(String[] args) { System.out.println("Enter an age"); Scanner scan=new Scanner(System.in); while (!scan.hasNextInt()) { //ask if the scanner has "something we want" System.out.println("Invalid age"); System.out.println("Enter an age"); scan.next(); //it doesn't have what we want, demand annother } int age = scan.nextInt(); //we finally got what we wanted, use it System.out.println("Your age was " + age); } }