簡體   English   中英

具有多種類型支持的Java Generics

[英]Java Generics with multiple type support

假設我們有這樣的界面......

interface ICalculator<T extends CalculableObject>{ void calculate(T obj); }

我們的泛型類型是一個抽象類...

public abstract class CalculableObject{...}

有多種具體類型......

public class TypeA extends CalculableObject{...}

public class TypeB extends CalculableObject{...}

您將如何定義Calculator對象的實現,該實現需要為多個CalculableObject類型定義計算方法?

即 -

public CalculatorAB<?> implements ICalculator{
void calculate(TypeA obj){...}
void calculate(TypeB obj){...}
}

因為類型擦除,你不能。 請參閱: 獲取通用接口的錯誤:接口Observer不能使用不同的參數多次實現:

我要做的是使用delgate並使用您的CalculatorAB,但它只是沒有實現ICalculator,或者更好的是,CalculatorAB實現了ICalcuator。 然后,您的方法可以檢查實例並轉發到適當的方法。

public CalculatorAB implements ICalculator<CalculableObject> {
  void calculate(CalculableObject obj){
    if(obj instanceof TypeA)
      calculate((TypeA)obj);
    else if(obj instanceof TypeB)
      calculate((TypeB)obj);
  }
  void calculate(TypeA obj){...}
  void calculate(TypeB obj){...}
}

你不能。 (與普遍看法相反,它可以相對容易地在沒有運行時具體化的情況下實現。但事實並非如此。)

通常,“主要”類型的多個子類型是一個壞主意。 有一個對象有返回適當的Calculator的方法(請不要匈牙利!)。

使用enum

public enum Type extends CalculableObject {
    A
    {
        @Override
        public void doSomething() { }
    },
    B;
}

然后保證TypeAB存在,並且它們都擴展了CalculableObject

這也使您能夠簡單地在傳遞Type.Acalculate方法作為Type CalculableObject ,而不是與A,B,C,d,等等弄亂它

我敢說,如果你想這樣做,也許在你的設計的其他地方有一些錯誤。 但除了已經提到的替代方案之外,您可以在接口中僅使計算方法通用,而不是整個接口。 然后子接口可以是通用的,或者只是定義所需的新方法。

像這樣:

public static abstract class CalculableObject{}

public static class TypeA extends CalculableObject{}
public static class TypeB extends CalculableObject{}
public static class TypeC extends CalculableObject{}

public interface ICalculator{
    <T extends CalculableObject> void calculate(T obj);
}

public static class CalculatorAB implements ICalculator{

    void calculate(TypeA obj){
        System.out.println("TypeA");
    }
    void calculate(TypeB obj){
        System.out.println("TypeB");
    }

    @Override
    public <T extends CalculableObject> void calculate(T obj) {
        System.out.println("CalculableObject");
    }
} 

public static void main(String args[]){
    TypeA a = new TypeA();
    TypeB b = new TypeB();
    TypeC c = new TypeC();

    CalculatorAB ab = new CalculatorAB();

    ab.calculate(a);
    ab.calculate(b); 
    ab.calculate(c);
}

這呈現

TypeA
TypeB
CalculableObject

您可以在CalculableObject類中定義“計算”所需的方法。 然后,在CalculatorAB中,您只需在給定對象上調用這些方法。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM