Created
October 19, 2017 17:48
-
-
Save Rahandi/16877b60214f779772de9f8c1af99961 to your computer and use it in GitHub Desktop.
ATM
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class Account | |
{ | |
private int accountNumber; // account number | |
private int pin; // PIN for authentication | |
private double availableBalance; // funds available for withdrawal | |
private double totalBalance; // funds available + pending deposits | |
// Account constructor initializes attributes | |
public Account(int theAccountNumber, int thePIN, double theAvailableBalance, double theTotalBalance){ | |
accountNumber = theAccountNumber; | |
pin = thePIN; | |
availableBalance = theAvailableBalance; | |
totalBalance = theTotalBalance; | |
} // end Account constructor | |
// determines whether a user-specified PIN matches PIN in Account | |
public boolean validatePIN(int userPIN){ | |
if(userPIN == pin){ | |
return true; // means the PIN input is match with the user's PIN | |
} | |
else{ | |
return false; // means the PIN input is not match with the user's PIN | |
} | |
} // end method validatePIN | |
// returns available balance | |
public double getAvailableBalance(){ | |
return availableBalance; | |
} | |
// returns the total balance | |
public double getTotalBalance(){ | |
return totalBalance; | |
} | |
// credits an amount to the account | |
public void credit(double amount){ | |
totalBalance += amount; // add to total balance | |
} | |
// debits an amount from the account | |
public void debit(double amount){ | |
availableBalance -= amount; // substract from available balance | |
totalBalance -= amount; // substract from total balance | |
} | |
// returns account number | |
public int getAccountNumber(){ | |
return accountNumber; | |
} | |
} // end class Account |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class ATM | |
{ | |
private boolean userAuthenticated; | |
private int currentAccountNumber; | |
private Screen screen; | |
private Keypad keypad; | |
private CashDispenser cashDispenser; | |
private DepositSlot depositSlot; | |
private BankDatabase bankDatabase; | |
private static final int BALANCE_INQUIRY = 1; | |
private static final int WITHDRAWAL = 2; | |
private static final int DEPOSIT = 3; | |
private static final int EXIT = 4; | |
public ATM(){ | |
userAuthenticated = false; | |
currentAccountNumber = 0; | |
screen = new Screen(); | |
keypad = new Keypad(); | |
cashDispenser = new CashDispenser(); | |
depositSlot = new DepositSlot(); | |
bankDatabase = new BankDatabase(); | |
} | |
public void run(){ | |
while(true){ | |
while(!userAuthenticated){ | |
screen.displayMessageLine("\nWelcome!"); | |
authenticateUser(); | |
} | |
performTransactions(); | |
userAuthenticated = false; | |
currentAccountNumber = 0; | |
screen.displayMessageLine("\nThank You!\nGoodbye!"); | |
} | |
} | |
private void authenticateUser(){ | |
screen.displayMessage("\nPlease enter your account number : "); | |
int accountNumber = keypad.getInput(); | |
screen.displayMessage("\nEnter your PIN : "); | |
int pin = keypad.getInput(); | |
userAuthenticated = bankDatabase.authenticateUser(accountNumber, pin); | |
if(userAuthenticated){ | |
currentAccountNumber = accountNumber; | |
} | |
else{ | |
screen.displayMessageLine("Invalid Account Number or PIN."); | |
screen.displayMessageLine("Please Try Again."); | |
} | |
} | |
private void performTransactions(){ | |
Transaction currentTransaction = null; | |
boolean userExited = false; | |
while(!userExited){ | |
int mainMenuSelection = displayMainMenu(); | |
switch(mainMenuSelection){ | |
case BALANCE_INQUIRY : | |
case WITHDRAWAL : | |
case DEPOSIT : | |
currentTransaction = createTransaction(mainMenuSelection); | |
currentTransaction.execute(); | |
break; | |
case EXIT : | |
screen.displayMessageLine("\nExiting the system..."); | |
userExited = true; | |
break; | |
default : | |
screen.displayMessageLine("\nYou did not enter a valid selection."); | |
screen.displayMessageLine("Please try again."); | |
break; | |
} | |
} | |
} | |
private int displayMainMenu(){ | |
screen.displayMessageLine("\nMain Menu :"); | |
screen.displayMessageLine("1 - View my balance"); | |
screen.displayMessageLine("2 - Withdraw cash"); | |
screen.displayMessageLine("3 - Deposit funds"); | |
screen.displayMessageLine("4 - Exit\n"); | |
screen.displayMessage("Enter a choice : "); | |
return keypad.getInput(); | |
} | |
private Transaction createTransaction(int type){ | |
Transaction temp = null; | |
switch(type){ | |
case BALANCE_INQUIRY : | |
temp = new BalanceInquiry(currentAccountNumber, screen, bankDatabase); | |
break; | |
case WITHDRAWAL : | |
temp = new Withdrawal(currentAccountNumber, screen, bankDatabase, keypad, cashDispenser); | |
break; | |
case DEPOSIT : | |
temp = new Deposit(currentAccountNumber, screen, bankDatabase, keypad, depositSlot); | |
break; | |
} | |
return temp; | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class BalanceInquiry extends Transaction | |
{ | |
// BalanceInquiry constructor | |
public BalanceInquiry(int userAccountNumber, Screen atmScreen, BankDatabase atmBankDatabase){ | |
super(userAccountNumber, atmScreen, atmBankDatabase); | |
} // end BalanceInquiry constructor | |
// performs the transaction | |
@Override | |
public void execute(){ | |
// get references to bank database and screen | |
BankDatabase bankDatabase = getBankDatabase(); | |
Screen screen = getScreen(); | |
// get the available balance for the account involved | |
double availableBalance = bankDatabase.getAvailableBalance(getAccountNumber()); | |
// get the total balance for the account involved | |
double totalBalance = bankDatabase.getTotalBalance(getAccountNumber()); | |
// display the balance information on the screen | |
screen.displayMessageLine("\nBalance Information : "); | |
screen.displayMessage(" - Available Balance : "); | |
screen.displayDollarAmount(availableBalance); | |
screen.displayMessage("\n - Total Balance : "); | |
screen.displayDollarAmount(totalBalance); | |
screen.displayMessageLine(""); | |
} // end method execute | |
} // end class BalanceInquiry |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class BankDatabase | |
{ | |
private Account[] accounts; // array of Accounts | |
// no-argument BankDatabase constructor initializes accounts | |
public BankDatabase(){ | |
accounts = new Account[2]; // just 2 accounts for testing | |
accounts[0] = new Account(12345, 54321, 1000.0, 1200.0); | |
accounts[1] = new Account(98765, 56789, 200.0, 200.0); | |
} // end no-argument BankDatabase constructor | |
// retrieve Account object containing specified account number | |
private Account getAccount(int accountNumber){ | |
// loop through accounts searching for matching account number | |
for(Account currentAccount : accounts){ | |
// return current account if match found | |
if(currentAccount.getAccountNumber() == accountNumber) return currentAccount; | |
} // end for | |
return null; // if no matching account was found, return null | |
} // end method | |
// determine whether user-specified account number and PIN match | |
// those of an account in the database | |
public boolean authenticateUser(int userAccountNumber, int userPIN){ | |
// attempt to retrieve the account with the account number | |
Account userAccount = getAccount(userAccountNumber); | |
if(userAccount != null){ | |
return userAccount.validatePIN(userPIN); | |
} | |
else{ | |
return false; // account number not found, so return false | |
} | |
} // end method | |
// return available balance of Account with specified account number | |
public double getAvailableBalance(int userAccountNumber){ | |
return getAccount(userAccountNumber).getAvailableBalance(); | |
} // end method | |
public double getTotalBalance(int userAccountNumber){ | |
return getAccount(userAccountNumber).getTotalBalance(); | |
} // end method | |
public void credit(int userAccountNumber, double amount){ | |
getAccount(userAccountNumber).credit(amount); | |
} // end method | |
public void debit(int userAccountNumber, double amount){ | |
getAccount(userAccountNumber).debit(amount); | |
} // end method | |
} // end class BankDatabase |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class CashDispenser | |
{ | |
// the default initial number of bills in the cash dispenser | |
private final static int INITIAL_COUNT = 500; | |
private int count; // number of $20 bills remaining | |
// no-argument CashDispenser constructor initializes count to default | |
public CashDispenser(){ | |
count = INITIAL_COUNT; // set count attribute to default | |
} // end CashDispenser constructor | |
// simulates dispensing of specified amount of cash | |
public void dispenseCash(int amount){ | |
int billsRequired = amount / 20; // number of $20 bills required | |
count -= billsRequired; // update the count of bills | |
} // end method dispenseCash | |
// indicates whether cash dispenser can dispense desired amount | |
public boolean isSufficientCashAvailable(int amount){ | |
int billsRequired = amount / 20; | |
if(count >= billsRequired){ | |
return true; // enough bills required | |
} | |
else{ | |
return false; // not enough bills required | |
} | |
} // end method isSufficientCashAvailable | |
} // end class CashDispenser |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class Deposit extends Transaction | |
{ | |
private double amount; // amount to deposit | |
private Keypad keypad; // references to keypad | |
private DepositSlot depositSlot; // references to deposit slot | |
private final static int CANCELED = 0; // constant for cancel option | |
// Deposit constructor | |
public Deposit(int userAccountNumber, Screen atmScreen, BankDatabase atmBankDatabase, Keypad atmKeypad, DepositSlot atmDepositSlot){ | |
// initializes superclass variables | |
super(userAccountNumber, atmScreen, atmBankDatabase); | |
// initialize references to keypad and deposit slot | |
keypad = atmKeypad; | |
depositSlot = atmDepositSlot; | |
} // end Deposit constructor | |
// perform transaction | |
@Override | |
public void execute(){ | |
BankDatabase bankDatabase = getBankDatabase(); // get reference | |
Screen screen = getScreen(); // get reference | |
amount = promptForDepositAmount(); // get deposit amount from user | |
// check whether the user entered a deposit amount or canceled | |
if(amount != CANCELED){ | |
// request deposit envelope containing specified amount | |
screen.displayMessage("\nPlease insert a deposit envelope containing "); | |
screen.displayDollarAmount(amount); | |
screen.displayMessage("."); | |
// receive deposit envelope | |
boolean envelopeReceived = depositSlot.isEnvelopeReceived(); | |
// check whether deposit envelope was received | |
if(envelopeReceived){ | |
screen.displayMessageLine("\nYour envelope has been received."); | |
screen.displayMessage("NOTE: The money just deposited will not be available until we verify the amount"); | |
screen.displayMessage("of any enclosed cash and your checks clear."); | |
// credit account to reflect the deposit | |
bankDatabase.credit(getAccountNumber(), amount); | |
} // end if | |
else{ | |
// deposit envelope not received | |
screen.displayMessageLine("\nYou did not insert an envelope"); | |
screen.displayMessageLine("So, the ATM has canceled your transaction."); | |
} // end else | |
} // end if | |
else{ | |
// user canceled instead of entering amount | |
screen.displayMessageLine("\nCanceling transaction..."); | |
} // end else | |
} // end method execute | |
// prompt user to enter a deposit amount in cents | |
private double promptForDepositAmount(){ | |
Screen screen = getScreen(); // get references to screen | |
// display the prompt | |
screen.displayMessage("\nPlease enter a deposit amount in CENTS (or 0 to cancel)"); | |
int input = keypad.getInput(); // receive input of deposit amount | |
// check whether the user canceled or entered a valid amount | |
if(input == CANCELED) return CANCELED; | |
else{ | |
return (double) input / 100; // return dollar amount | |
} // end else | |
} // end method | |
} // end class Deposit |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class DepositSlot | |
{ | |
// indicate whether envelope was received (always returns true) | |
// because this is only a software simulation of a real deposit slot | |
public boolean isEnvelopeReceived(){ | |
return true; // deposit envelope was received | |
} // end method isEnvelopeReceived | |
} // end class DepositSlot |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import java.util.Scanner; | |
public class Keypad | |
{ | |
private Scanner input; // reads data from the command line | |
// no-argument constructor initializes the Scanner | |
public Keypad(){ | |
input = new Scanner(System.in); | |
} // end no-argument Keypad constructor | |
// return an integer value entered by user | |
public int getInput(){ | |
return input.nextInt(); // we assume that user enters an integer | |
} // end method getInput | |
} // end class Keypad |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class Screen | |
{ | |
// display a message without a carriage return | |
public void displayMessage(String message){ | |
System.out.print(message); | |
} // end method displayMessage | |
// display a message with a carriage return | |
public void displayMessageLine(String message){ | |
System.out.println(message); | |
} // end method displayMessageLine | |
// displays a dollar amount | |
public void displayDollarAmount(double amount){ | |
System.out.printf("$%,.2f", amount); | |
} // end method displayDollarAmount | |
} // end class Screen |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public abstract class Transaction | |
{ | |
private int accountNumber; // indicates account involved | |
private Screen screen; // ATM's screen | |
private BankDatabase bankDatabase; // account info database | |
// Transaction constructor invoked by subclasses using super() | |
public Transaction(int userAccountNumber, Screen atmScreen, BankDatabase atmBankDatabase){ | |
accountNumber = userAccountNumber; | |
screen = atmScreen; | |
bankDatabase = atmBankDatabase; | |
} // end Transaction constructor | |
// return account number | |
public int getAccountNumber(){ | |
return accountNumber; | |
} // end method | |
// return reference to screen | |
public Screen getScreen(){ | |
return screen; | |
} // end method | |
// return reference to bank database | |
public BankDatabase getBankDatabase(){ | |
return bankDatabase; | |
} // end method | |
// perform the transaction (overridden by each subclass) | |
abstract public void execute(); | |
} // end class Transaction |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class Withdrawal extends Transaction | |
{ | |
private int amount; // amount to withdraw | |
private Keypad keypad; // references to keypad | |
private CashDispenser cashDispenser; // references to cash dispenser | |
// constant corresponding to menu option to cancel | |
private final static int CANCELED = 6; | |
// Withdrawal constructor | |
public Withdrawal(int userAccountNumber, Screen atmScreen, BankDatabase atmBankDatabase, Keypad atmKeypad, CashDispenser atmCashDispenser){ | |
// initializes superclass variables | |
super(userAccountNumber, atmScreen, atmBankDatabase); | |
// initializes references to keypad and cash dispenser | |
keypad = atmKeypad; | |
cashDispenser = atmCashDispenser; | |
} // end Withdrawal constructor | |
// perform transaction | |
@Override | |
public void execute(){ | |
boolean cashDispensed = false; // cash was not dispensed yet | |
double availableBalance; // amount available for withdrawal | |
// get references to bank database and screen | |
BankDatabase bankDatabase = getBankDatabase(); | |
Screen screen = getScreen(); | |
// loop until cash is dispensed or the user cancels | |
do{ | |
// obtain a chosen withdrawal amount from the user | |
amount = displayMenuOfAmounts(); | |
// check whether user choose a withdrawal amount or canceled | |
if(amount != CANCELED){ | |
// get available balance of account involved | |
availableBalance = bankDatabase.getAvailableBalance(getAccountNumber()); | |
// check whether the user has enough money in the account | |
if(amount <= availableBalance){ | |
// check whether the cash dispenser has enough money | |
if(cashDispenser.isSufficientCashAvailable(amount)){ | |
// update the account involved to reflect the withdrawal | |
bankDatabase.debit(getAccountNumber(), amount); | |
cashDispenser.dispenseCash(amount); // dispense cash | |
cashDispensed = true; // cash was dispensed | |
// instructs user to take cash | |
screen.displayMessageLine("\nYour cash has been dispensed. Please take your cash now."); | |
} // end if | |
else{ | |
// cash dispenser does not have enough cash | |
screen.displayMessageLine("\nInsufficient cash available in the ATM."); | |
screen.displayMessageLine("\nPlease choose a smaller amount."); | |
} // end if | |
} // end if | |
else{ | |
// not enough money available in user's account | |
screen.displayMessageLine("\nInsufficient funds in your account."); | |
screen.displayMessageLine("\nPlease choose a smaller amount."); | |
} // end if | |
} // end if | |
else{ | |
// user choose cancel menu option | |
screen.displayMessageLine("\nCancelling transactions..."); | |
return; // return to main menu because user canceled | |
} // end if | |
} while(!cashDispensed); | |
} // end method execute | |
// display a menu of withdrawal amounts and the options to cancel | |
// return the chosen amount or 0 if the user chooses to cancel | |
private int displayMenuOfAmounts(){ | |
int userChoice = 0; // local variable to store return value | |
Screen screen = getScreen(); // get screen references | |
// array of amounts to correspond to menu numbers | |
int[] amounts = {0, 20, 40, 60, 100, 200}; | |
// loop while no valid choice has been made | |
while(userChoice == 0){ | |
// display the withdrawal menu | |
screen.displayMessageLine("\nWithdrawal Menu : "); | |
screen.displayMessageLine("1 - $20"); | |
screen.displayMessageLine("2 - $40"); | |
screen.displayMessageLine("3 - $60"); | |
screen.displayMessageLine("4 - $100"); | |
screen.displayMessageLine("5 - $200"); | |
screen.displayMessageLine("6 - Cancel Transaction"); | |
screen.displayMessage("\nChoose a withdrawal amount : "); | |
int input = keypad.getInput(); // get user input through keypad | |
// determine how to proceed based on the input value | |
switch(input){ | |
// if the user choose a withdrawal amount | |
// i.e choose option 1, 2, 3, 4 or 5 | |
// return the corresponding amount from amounts's array | |
case 1 : | |
case 2 : | |
case 3 : | |
case 4 : | |
case 5 : | |
userChoice = amounts[input]; // save user's choice | |
break; | |
case CANCELED : | |
// the user choose to cancel | |
userChoice = CANCELED; // save user's choice | |
break; | |
default : | |
// the user did not enter value between 1-6 | |
screen.displayMessageLine("\nInvalid selection."); | |
screen.displayMessageLine("Try again."); | |
} // end switch | |
} // end while | |
return userChoice; // return withdrawal amount or CANCELED | |
} // end method displayMenuOfAmounts | |
} // end class Withdrawal |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
I have doubt . U have written all the class as public class . U have written separately all public class . How to done this in command prompt to run all in one .