2016-01-15 200 views
1

我在使用Java中的泛型時遇到了鑄造問題。 我試圖提供一個小例子來解釋我的問題。Java泛型在接口之間鑄造

IVariable.java

public interface IVariable { 
} 

IProblem.java

public interface IProblem<V extends IVariable> { 
} 

Algorithm.java

public class Algorithm<V extends IVariable, P extends IProblem<V>> { 

    public void doSomething(P problem) { 

     // ERROR: Type mismatch: cannot convert from P to IProblem<IVariable> 
     IProblem<IVariable> genericProblem = problem; 

    } 

} 

爲什麼我需要明確地投下變量genericProblem到

@SuppressWarnings("unchecked") 
IProblem<IVariable> genericProblem = (IProblem<IVariable>) problem; 

並得到警告?

該方法將P作爲類型IProblem的參數,因爲V也必須實現IVariable。 我的錯誤在哪裏?什麼是解決方法?

我不想寫

IProblem<V> genericProblem = problem; 

因爲問題的輸入變量可能會有所不同。 無論如何,在我看來,IProblem<V>IProblem<IVariable>更具體。

在此先感謝!

回答

2

IProblem<V>並不等同於一個IProblem<IVariable>,即使V被constrainted是一個IVariable,因爲Java的泛型是不變的。當然,IProblem<V>是要走的路,但如果你不想這樣,你可以使用上界通配符來表達VIVariable之間的關係,而不是:

IProblem<? extends IVariable> genericProblem = problem; 
1

的泛型類型必須是一個完全符合。 V extends IVariableIVariable不是可互換的類型。讓我舉另一個例子。

List<Integer> ints = new ArrayList<>(); // list of ints. 
List<Number> nums = ints; // doesn't compile but this is what you are trying to do 
nums.add(new BigDecimal(0.0)); // fine as BigDecimal is a Number.