Java泛型难题

时间:2010-10-12 14:03:46

标签: java generics

以下是相关代码:

public interface Artifact {}    
public interface Bundle implements Artifact {}
public interface Component implements Artifact {}

public interface State<T extends Artifact> {
    void transition(T artifact, State<T> nextState);
}

这允许我定义这个枚举:

enum BundleState implements State<Bundle> {

    A, B, C;

    public void transition(Bundle bundle, State<Bundle> nextState) {}
    }
}

但我想要的方法签名是:

    public void transition(Bundle bundle, BundleState nextState) {}
    }

但是这不能编译。显然问题在于我如何在T界面中定义State,但我不知道如何修复它。

谢谢, 唐

4 个答案:

答案 0 :(得分:10)

事情可能会开始变得笨拙,但你可以State更改为:

public interface State<T extends Artifact, U extends State<T, U>> {
    void transition(T artifact, U nextState);
}

将BundleState更改为:

public enum BundleState implements State<Bundle, BundleState> {
    A, B, C;

    public void transition(Bundle bundle, BundleState nextState) {}
}

答案 1 :(得分:3)

Java中的方法不是逆变的。你可以超载并且两者兼而有之,但是没有多大意义。

可能您可以将State声明为:

public interface State<THIS extends State<THIS, A>, A extends Artifact> {
    void transition(A artifact, THIS nextState);
}

THIS extends State<THIS, A>可能是错误的。这取决于你想做什么。

(单字母枚举常量可能是一个坏主意,特别是与泛型参数混合时。)

答案 2 :(得分:1)

transition(Bundle,BundleState)与您当前的State接口不匹配,除非您按照其他人的建议更改它。您还可以使用

保留界面
enum BundleState implements Artifact, State<BundleState> {
    A, B, C;
    public void transition(BundleState bundle, State<BundleState> nextState)
    {
    }
}

答案 3 :(得分:0)

enum BundleState implements State<Bundle> 
{
    A, B, C;

    public void transition(Bundle bundle, BundleState nextState) 
    {
        transition(bundel, (State<Bundle>)nextState);
    }

    public void transition(Bundle bundle, State<Bundle> nextState) {}
}