2016-12-15 37 views
0

通配符通用數據類型的我有這個類:通通用在Java

public interface DataAccessor<E extends Model, U> 

public class Data<T> implements DataMenuItemObservable<T> { 

這個接口:

interface Listener<T> { 
    void onResponse(T value); 
} 

這個方法:

public interface DataAccessor<E extends Model, U> extends DataMenuItemObservable<E> { 

... 

    public DataAccessor<? extends Model, ?> getPrimaryDataAccessor() 

    void get(int index, Context context, Listener<Data<E>> listener, ErrorListener errorListener); 

... 

} 

,並獲得此編譯器錯誤代碼:

DataAccessor<? extends Model, ?> accessor = db.getPrimaryDataAccessor(); 
accessor.get(0, this, new DataAccessor.Listener<Data<? extends Model>>() { 
      @Override 
      public void onResponse(Data<? extends Model> value) { 
      } 
     }, this); 

想法說incompatible types: <anonimous Listener<Data<? extends Model>>> cannot be converted to Listener<Data<CAP#1>>

我也試圖與this但同樣的錯誤實現接口。

如何解決錯誤? 是否有一些可接受的解決方法?

+0

什麼的'DataAccessor.get()'簽名? – shmosel

+0

什麼是數據? – shmosel

+0

@shmosel更新 – nikartix

回答

3

它不起作用的原因是因爲編譯器不知道兩個通配符(? extends Model)是否實際引用相同的類型。您可以解決此通過創建一個輔助方法來捕獲類型:

private <E extends Model> void get(DataAccessor<E, ?> accessor); 
    accessor.get(0, this, new DataAccessor.Listener<Data<E>>() { 
     @Override 
     public void onResponse(Data<E> value) { 
      //... 
     } 
    }, this); 
} 

現在所說的幫手:

DataAccessor<? extends Model, ?> accessor = db.getPrimaryDataAccessor(); 
get(accessor); 
+0

謝謝!它的工作原理 – nikartix

2

Shmosel有一個很好的解決方案。我只想補充一點,如果你有Java的8,你可以使用lambda可以推斷出正確的類型,違背了一個匿名類:

DataAccessor<? extends Model, ?> accessor = db.getPrimaryDataAccessor(); 
accessor.get(0, this, value -> { 
     // code 
    }, this); 
+0

我沒有意識到這一點。非常好。 – shmosel