2011-05-08 11 views
5

Estoy intentando producir algunas clases para controlar una aplicación modelo-vista-presentador. He llegado a las siguientes definiciones, pero estoy luchando para evitar los genéricos recursivos.Posiblemente recursivos genéricos Java entre dos clases

public abstract class Presenter<V extends View<...?>> { 

    protected V view; 

    public Presenter(V view) { 
    this.view = view; 
    } 

    // ... 
} 


public abstract class View<P extends Presenter<...?>> { 

    protected P presenter; 

    // ... 
} 

Quería imponer una relación mutua entre las dos clases. La idea es que podría instanciar un presentador para una vista particular, con ambas clases confiando en métodos útiles definidos en las clases base abstractas, pero ambos sabiendo exactamente qué subclase de la clase abstracta de contraparte está en uso.

Mi problema es la definición de la parte ..? del código. No puedo ver una manera de evitar una situación recurrente, tales como:

public abstract class View<P extends Presenter<V>, V extends View<Q>, Q extends...> 

e incluso esa definición no es constante, ya que la clase View ahora toma dos parámetros genéricos ... confusión masiva.

básicamente quería evitar las clases están llenas de referencias al tipo de clase abstracta, lo que exige una gran cantidad de fundición a través de las implementaciones concretas, como a continuación:

// simpler option 

public abstract class Presenter { 

    protected View view;  

    public Presenter(View view) { 
    this.view = view; 
    } 
} 

public class FooPresenter extends Presenter { 

    public FooPresenter(BarView view) { 
    super(view); 
    } 

    public someMethod() { 
    ((BarView) getView()).viewSpecificMethod(); 
    } 
} 

Cada aplicación concreta de estas clases se necesitaría constantemente emitir desde el tipo abstracto al tipo que "sabe" está en uso.

Respuesta

1

Trate

public abstract class Presenter<V extends View<? extends Presenter<?>>> 

y

public abstract class View<P extends Presenter<? extends View<?>>> 

Esto restringiría a los presentadores tienen ninguna vista como su parámetro genérico y vistas a tener ningún presentador.

+0

Excelente, eso se hace el truco! Gracias. –

3

utilizar un segundo parámetro de tipo para el tipo de this:

class Presenter<P extends Presenter<P,V>, V extends View<P,V>> { 
    V view; 
} 

class View<P extends Presenter<P,V>, V extends View<P,V>> { 
    P presenter; 
} 

class MyPresenter extends Presenter<MyPresenter, MyView>{} 

class MyView extends View<MyPresenter, MyView>{} 

entonces usted puede hacer:

MyPresenter mp = new MyPresenter().view.presenter; 
+0

Gracias por la respuesta. ¿Este diseño ofrece ventajas sobre la solución actual? Además, ¿es necesaria la cláusula '.view.presenter'? –

+0

@Duncan Jones "¿Este diseño ofrece ventajas sobre la solución actual?" como @Thomas dijo, "Esto restringiría a los presentadores a tener cualquier vista como su parámetro genérico y vistas para tener cualquier presentador". Estoy convencido de que ESTA es la respuesta correcta, ya que estoy bastante seguro de que el otro puede tener un hoyo de tipo, aunque no tengo tiempo para demostrarlo en este momento. – ArtB