Visitor = wizytator, odwiedzający.
Zadanie programistyczne
Potrzebujemy klasy, której obiekt będzie odwiedzał obiekty innych klas i
i wykonywał na nich pewne operacje. Np. mamy klasę Pracownik i klasę dziedziczącą
Kierownik. Chcemy zsumować dni urlopu (albo zarobki, itd).
Rozwiązanie
Trzeba użyć wzorca Visitor
(Wizytator).
Tworzymy klasę abstrakcyjną Visitor
zawierająca metodę visit
dla każdej klasy
którą będziemy wizytować (te klasy nie muszą być koniecznie 'rodziną’. Mogą to być zupełnie nie związane klasy.
W klasie Pracownik
oraz w klasie Kierownik
dodajemy metodę accept
dla tego
Visitora
. Tworzymy klasy konkretne dziedziczące po klasie abstrakcyjnej.
po jednej dla każdego wizytatora: pierwszy zlicza dni urlopu, drugi
zlicza dni urlopu oraz dni dodatkowego urlopu przysługującego kadrze
kierowniczej. Są to TotalUrlopVisitor
i ZwyklyUrlopVisitor
.
Tworzymy klasę Main
w ktorej wskazujemy wszystkie obiekty do odwiedzenia
i uruchamiamy metodę accept()
każdego obiektu.
Kody
Klasa Visitor
package visitor; public abstract class Visitor { public abstract void visit(Pracownik pracownik); public abstract void visit(Kierownik kierownik); }
Klasa TotalUrlopVisitor
package visitor; public class TotalUrlopVisitor extends Visitor { private int sumaDni; public TotalUrlopVisitor() { sumaDni = 0; } public int getSumaDni() { return sumaDni; } @Override public void visit(Kierownik kierownik) { sumaDni += kierownik.getUrlop(); sumaDni += kierownik.getUrlopDodatkowy(); } @Override public void visit(Pracownik pracownik) { sumaDni += pracownik.getUrlop(); } }
Klasa ZwyklyUrlopVisitor
package visitor; public class ZwyklyUrlopVisitor extends Visitor { private int sumaDni; public ZwyklyUrlopVisitor() { sumaDni = 0; } public int getSumaDni() { return sumaDni; } @Override public void visit(Kierownik kierownik) { sumaDni += kierownik.getUrlop(); } @Override public void visit(Pracownik pracownik) { sumaDni += pracownik.getUrlop(); } }
Klasa Pracownik
package visitor; public class Pracownik { private int zwolnienia, urlop; private double pensja; private String nazwisko; public Pracownik(String nazwisko, double pensja, int urlop, int zwolnienia) { this.urlop = urlop; this.zwolnienia = zwolnienia; this.pensja = pensja; this.nazwisko = nazwisko; } public int getZwolnienia() { return zwolnienia; } public void setZwolnienia(int zwolnienia) { this.zwolnienia = zwolnienia; } public int getUrlop() { return urlop; } public void setUrlop(int urlopy) { this.urlop = urlopy; } public double getPensja() { return pensja; } public void setPensja(double pensja) { this.pensja = pensja; } public String getNazwisko() { return nazwisko; } public void setNazwisko(String nazwisko) { this.nazwisko = nazwisko; } public void accept(Visitor visitor) { visitor.visit(this); } }
Klasa Kierownik
package visitor; public class Kierownik extends Pracownik { private int urlopDodatkowy; public Kierownik(String nazwisko, double pensja, int urlopy, int zwolnienia) { super(nazwisko, pensja, urlopy, zwolnienia); } public int getUrlopDodatkowy() { return urlopDodatkowy; } public void setUrlopDodatkowy(int urlopDodatkowy) { this.urlopDodatkowy = urlopDodatkowy; } @Override public void accept(Visitor visitor) { visitor.visit(this); } }
Klasa Main
package visitor; public class Main { private Pracownik[] pracownicy; public Main() { pracownicy = new Pracownik[7]; int i = 0; pracownicy[i++] = new Pracownik("A.A.", 55000, 12, 1); pracownicy[i++] = new Pracownik("A.B.", 150000, 9, 0); pracownicy[i++] = new Pracownik("F.H", 50000, 15, 2); pracownicy[i++] = new Pracownik("D.O", 57000, 12, 2); pracownicy[i++] = new Pracownik("L. T", 100000, 20, 6); Kierownik b = new Kierownik("L.S", 175000, 16, 4); b.setUrlopDodatkowy(12); Kierownik b1 = new Kierownik("M.B", 35000, 17, 6); b1.setUrlopDodatkowy(17); pracownicy[i++] = b; pracownicy[i++] = b1; ZwyklyUrlopVisitor zuv = new ZwyklyUrlopVisitor(); TotalUrlopVisitor vac = new TotalUrlopVisitor(); for (int j = 0; j < pracownicy.length; j++) { pracownicy[j].accept(vac); pracownicy[j].accept(zuv); } System.out.println("Liczba wszystkich dni urlopu do wykorzystania: " + Integer.valueOf(vac.getSumaDni())); System.out.println("Liczba dni zwykłych do wykorzystania: " + Integer.valueOf(zuv.getSumaDni())); } // ----------------------------------------- static public void main(String argv[]) { new Main(); } }
Wynik
Liczba wszystkich dni urlopu do wykorzystania: 130 Liczba dni zwykłych do wykorzystania: 101