De ce vreau ca această clasă să extindă o interfață și care este modelul de proiectare potrivit pentru acest lucru? (Inginerie software, Java, Modele De Design)

Jared K a intrebat.

Să presupunem că am o interfață Employee și există multe clase care o implementează, cum ar fi Bob, Joe, și Mary, dintre care niciuna nu poate fi modificată.

public interface Employee{
  public void work()
}

public class Mary implements Employee{
  public void work(){
    //Mary's implementation of work
  }
}

Trebuie să fac un Manager care să fie un înveliș pentru o clasă Employee obiect. Astfel, constructorul pentru Manager ia un obiect de tip Employee

Public class Manager{
private Employee employee;

  public Manager(Employee employee){
     this.employee = employee;
  }

  public void work(){
    this.employee.work()
  }

  public void manage(){
     //my implementation of manage
  }


}

Când un Manager este instanțiat, acesta ar trebui să aibă toate metodele clasei de bază Employee plus câteva în plus. Cele mai multe dintre metodele obiectului subiacent Employee nu vor fi suprascrise (a se vedea work) și, prin urmare, cred că ar trebui să extind Employee. Dar o clasă nu poate extinde o interfață. În prezent, lucrez la declararea fiecăreia dintre clasele Employee în cadrul clasei Manager clasă și să le fac să apeleze pur și simplu metoda corespunzătoare Employee metoda corespunzătoare. Dar acest lucru pare a fi o procedură inutilă și se va întrerupe dacă interfața Employee se va schimba vreodată.

Din moment ce nu este permisă extinderea unei interfețe, care este modelul de proiectare corect pentru ceea ce încerc să fac?

Comentarii

  • De când nu se poate extinde o interfață? De fapt, o subinterfață utilizează extends atunci când extinde o superinterfață în Java. – user22815
  • Omul de zăpadă: O interfață poate extinde o interfață, dar o clasă nu poate extinde o interfață. Aș putea face o ManagerInterface extends Employee dar atunci aș putea face Manager implements ManagerInterface tot ar trebui să declar o implementare pentru fiecare metodă din Employee și din ManagerInterface, lăsându-mă de unde am plecat. –  > Por Jared K.
3 răspunsuri
Jules

Modul în care o faci este practic modul obișnuit de a face acest lucru într-un limbaj static. Probabil că ar trebui să vă declarați Manager pentru a implementa Employee, dar, în afară de asta, nu există o modalitate mai bună de a obține rezultatul pe care îl doriți.

În unele limbaje cu tipare dinamică (de exemplu, Ruby sau Smalltalk) există o altă alternativă: puteți implementa o metodă care este apelată dacă obiectul dvs. primește un mesaj nerecunoscut (adică este apelat cu o metodă despre care nu știe), iar apoi puteți transmite acel mesaj către obiectul țintă. Java nu are nicio modalitate de a face acest lucru.

Comentarii

  • dacă Manager implementează Employee, ce se întâmplă atunci când treceți din greșeală un Employee deja Manager ca parametru pentru un nou Manager? –  > Por uylmz.
uberbrodt

Nu aveți nevoie de moștenire în acest caz, ci de compoziție:

public interface Manager {
    void manage();
}

public class Mary implements Employee, Manager{
    public void work(){
        //Mary's implementation of work
    }

    public void manage(){
        //manage
    }
}

Java permite claselor să implementeze mai multe interfețe și este un bun ghid: De ce ar trebui să prefer compoziția în locul moștenirii?

Dacă literalmente nu puteți schimba Mary clasa, atunci ar trebui să faceți un obiect wrapper ca cel pe care îl aveți, care ar acționa ca un adaptor pentru instanțele clasei Employee.

Nu cred că este nevoie să extindeți interfața Employee, deoarece nu ați indicat că va avea nevoie de o interfață de tip work() metodă.

Fabio

Ați spus Trebuie să realizez o clasă Manager care să fie un wrapper pentru un obiect Employee Scopul învelișului este exact ceea ce ați descris, învelind un alt comportament sub propriile metode.

Cred că Manager trebuie să implementeze Employee interfața.

Public class Manager implements Employee
{
    private Employee employee;

    public Manager(Employee employee)
    {
        this.employee = employee;
    }

    public void work()
    {
        this.employee.work();
    }

    public void manage()
    {
        //my implementation of manage
    }
}

În cazul de față Manager clasa înfășoară comportamentul lui Employee interfață și o extinde cu propriul comportament de manager.