我想创建一个接口(interface):

public interface OperandValue
{
    <T> T getValue();
}

然后,我想有一个像这样的具体实现:
public class NumberOperandValue implements OperandValue
{
    @Override
    public <Integer> Integer getValue()
    {
        // some integer value that is set elsewhere
        return 1;
    }
}

Eclipse强调<Integer>给我一个警告,上面写着:



感谢您提出关于是否可以正常工作的任何建议。我意识到我可以在接口(interface)级别而不是方法级别定义泛型,但是如果可能的话,我想尝试使其通用。

最佳答案

您可能希望将接口(interface)更改为:

public interface OperandValue<T>
{
    T getValue();
}

并执行到:
public class NumberOperandValue implements OperandValue<Integer>
{
    @Override
    public Integer getValue()
    {
        // some integer value that is set elsewhere
        return 1;
    }
}

现在,您要告诉接口(interface)您希望该方法返回什么类型。换句话说,您正在使接口(interface)类型通用,而不是方法声明。但这似乎就是您想要的。

附带说明:
public <Integer> Integer getValue()

实际上意味着“用名称“Integer”定义通用类型参数”,其中getValue返回您刚定义的“Integer”类型。

下面回应史蒂夫的评论:



该警告消息表明您在使用Java泛型时违反了规则。要了解原因,请在删除<Integer>类型参数之前考虑一下方法签名的含义。
public <Integer> Integer getValue()

此签名意味着getValue方法返回Integer类型的值,其中Integer定义为您在尖括号之间定义的通用类型参数。字符串Integer的含义完全是任意的,并且与以下内容完全相同:
public <T> T getValue()

为了清楚起见,让我们坚持使用此版本的方法签名来解决问题。当我们删除类型参数时会发生什么?
public T getValue()

现在,如果您尝试进行编译,则会收到一个错误消息,即T未定义。但是,由于您的原始类型签名使用Integer声明了类型参数,因此在删除它时,留下了:
public Integer getValue()

因为Integer已经是预定义的类型,所以方法签名在技术上仍然合法。但是,类型参数的名称恰好与已经存在的类型相同只是偶然的。

此外,由于您的接口(interface)已经使用泛型声明了方法签名,因此当您从实现中将其删除时,Java编译器会生成警告。具体地说,编译器担心在基类中,方法的返回类型是(类型擦除为Object)通用参数Integer,该参数不是同一类型(也不知道与该类型兼容)系统类,名称为Integer(或精确地说是java.lang.Integer)。

10-01 18:47
查看更多