Treść zadania:
Twoim zadaniem jest przygotowanie oprogramowania do bankomatów "Szmallenium". Bankomat nie ma być aktywny gdy nikt nie użył karty płatniczej. Jeśli karta, została użyta, bankomat prosi o wpisanie numeru pin do karty. Jeśli pin trzykrotnie został wprowadzony błędnie to bankomat zablokuje kartę i nie będzie już jej więcej użyć. Po poprawnym wprowadzeniu pinu - ilość nieudanych prób wpisania pinu zostaje sprowadzona do zera, a klient może przystąpić do wypłaty gotówki (Zakładamy że klient ma kasę) , wtedy bankomat sprawdza czy ma odpowiednią ilość gotówki i wypłaca, jeśli nie ma wystarczająco, proponuje wypłatę gotówki o niższej kwocie.Jeśli nie ma gotówki to jest zablokowany i nikt nie może korzystać z bankomatu. Użyj wzorca projektowego stan:
Jeśli, ktokolwiek całe przeczyta , prosiłbym o wszelkie sugestię, najbardziej te dotyczące budowy klas i szablonu oraz czy spełnia to założenia wzorca stan. Z góry dziękuje.
Oprócz tego mam drobny problem inicjacją metody run w klasie Runner. Nie chcę przyjmować argumentów ;/ oraz klasa windowsApps nie wykonuje czyszczenia konsoli. (Szczegóły na dole tematu)
Kod jest zrealizowany do etapu łączenia się z bankomatem.
Klasa główna:
package bankonet; import bankonet.windowsPackage.WindowsApps; import bankonet.windowsPackage.RunnerApps; import java.util.ArrayList; import java.util.List; import java.util.Scanner; public class BankoNET { public static void main(String[] args) { User user = new User (0,"11",false); initSystem(user); }
Pakiety arrayList, list czy Scanner, nie muszę tłumaczyć. windowsPackage są to klasy pomocnicze (wątki,czyszczenie konsoli).
Tworzymy obiekt user o klasie user. Przyjmuje trzy własności. (licznik,pin, oraz stan karty usera).
Pytanie: Czy tu już trzeba wykorzystać model Obserwatora? który po przez wywołanie eventu [Insert Card], odwoła się do klas z pakietu CashMachine (obecnie tylko initSystem)?
Metoda initSystem
private static boolean initSystem(User user) { Scanner input = new Scanner(System.in); RunnerApps mainThread = new RunnerApps(); UserObserver observer = new UserObserver(user); Validator valid = new Validator(user); while(valid.isInitValid()) { if (observer.checkUser()){ for (int i = 0; i < 3; i++){ System.out.println("Account is Blocked!!!!!"); mainThread.run(); } return false ; } System.out.println("---Szmalcium----"); System.out.println("We able to carry your money"); mainThread.run(); WindowsApps appsFunc = new WindowsApps(); appsFunc.clearConsole(); System.out.println("Please insert credic card"); mainThread.run(); WindowsApps.clearConsole(); System.out.println("Please write PIN"); String usedPassword = input.nextLine(); mainThread.run(); System.out.println("Verify...Please wait"); WindowsApps.clearConsole(); if (valid.isCorect(usedPassword)) { System.out.println("Conect to bankAccount"); return true; } System.out.println("Password is incorect"); } return true; }
Tworzone są następne obiekty userObserver z klasy Observer, valid z klasy Validator. Do obydwóch przekazuje utworzony obiekt. Zastanawiałem się nad ustawieniem klasy user jako nadrzędną, ale to trochę głupie , klasa nadrzędna, z tego co pamiętam ma dostęp do klas podrzędnych i do ich metod (trochę słabo by user widział jak wygląda walidacja). No chyba, że ustawić je jako protected? (oczywiście do metod :))
Wywołujemy metodę, sprawdzająca czy nastąpiła inicjacja validacji oraz czy validacja..Obserwator sprawdza status karty, jeśli jest zablokowana wychodzi z metody, przerywając jakby zdarzenie [insertCard] , obecnie kończy program.
Jeśli nie, uruchamiamy wątek (obecnie tylko przerywa działanie na 2 sekundy, nie ma multiThread ), pobieramy dane i sprawdzamy czy dane są prawidłowe, inicjując metodę isCorect, przekazując w parametrze obiekt typu String o nazwie usedPassword, który przejmuje wartości od obiektu input z klasy Scanner). Jeśli validacja przebiegła nieprawidłowo, metoda zagniedżona w isCorect zwiększa licznik o 1 i następuje powtórka :), jeśli prawidłowo, łączymy się z bankomatem.
Klasa User
package bankonet; public class User { private int counter; private String password = ""; private boolean isBlock; public String getPassword() { return password; } public int getCounter() { return counter; } public void setCounter(int counter) { this.counter = counter; } User (int counter, String password, boolean isBlock){ this.counter = counter; this.password = password; this.isBlock = isBlock; }
Tu nie ma co opisywać. Chyba wszystko logiczne.
Klasa: User
package bankonet; public class UserObserver { private User user; public UserObserver(User user) { this.user = user; } public boolean checkUser(){ if (user.getCounter() == 3){return true;} return false; } }
Pierwszy obserwator.
Klasa: Validator
package bankonet; import java.util.List; public class Validator{ private User user; private boolean initValid = true; public Validator( User user) { this.user=user; } public boolean isCorect(String inputPIN) { String usedString = user.getPassword(); if (usedString.equals(inputPIN)) { initValid = false; return true; } addCounter(); return false; } public boolean isInitValid() { return initValid; } private void addCounter() { int nowCounter = user.getCounter(); int afterCounter = nowCounter + 1; user.setCounter(afterCounter); } }
Tutaj chyba nie muszę nic tłumaczyć :).
Klasa: Runner z pakietu:WindowApps + interface.
package bankonet.windowsPackage; import java.util.logging.Level; import java.util.logging.Logger; public class RunnerApps implements Runnable { public void run() { try { Thread.sleep(2000); } catch (InterruptedException ex) { Logger.getLogger(RunnerApps.class.getName()).log(Level.SEVERE, null, ex); } } }
interface Runabble { public void run (int timer); }
I tu mam problem, próbowałem zainicjować metodę z parametrem, ale klasa na to mi nie pozwala, chociaż w intefejsie zaznaczyłem, że metoda ma mieć parametr. Może, należy ją wywołować po przez super.run()?
Pakiet: windowsPackage Klasa: windowsApps.
package bankonet.windowsPackage; import java.io.IOException; /** * * @author Patryk */ public class WindowsApps { public final static void clearConsole() { try { final String os = System.getProperty("os.name"); if (os.contains("Windows")) { Runtime.getRuntime().exec("cls"); } else { Runtime.getRuntime().exec("clear"); } } catch (final Exception e) { // Handle any exceptions. } }
Wcześniej robiła co należy , teraz nie chcę ;/. Żadnymi warningami nie rzuca.
Uff ale się rozpisałem....