Java枚举实现了具有Class <t>返回类型的接口

时间:2015-05-28 20:25:09

标签: java generics enums

好的,好的。

这是一个实现带有返回“原始类型”的方法的接口的枚举,它给出了关于接口中getCaste()方法的警告。

public enum Thing implements HasCaste {

    Type1 {
        @Override
        public Class getCaste() {
            return String.class;
        }
    };
}

interface HasCaste {
    public Class getCaste();
}

如果我将界面的方法更改为:

public <T> Class<T> getCaste();

它会更改为Type1方法签名上未经检查的警告。如果我然后将Type1.getCaste()的签名更改为:

public <T> Class<T> getCaste()

然后返回具有不兼容的类型错误,因为Class<String>无法转换为Class<T>。如果我然后将返回值更改为(Class<T>) String.class,我们会收到未经检查的投射警告。

有没有办法在没有警告的情况下这样做?

编辑:

抱歉,我之前没有添加此内容,但这样做很好:

  , Type2 {
        @Override
        public Class getCaste() {
            return Integer.class;
        }
    };

3 个答案:

答案 0 :(得分:2)

正如在question I asked a while ago that was linked by Radiodef中确定的那样,你不能用enum来做,只能通过实际上是类的模拟枚举来实现,就像这样。

public abstract class Thing<T> implements HasCaste<T> {
    public static final Thing<String> Type1 = new Thing<String>() {
        @Override
        public Class<String> getCaste() {
            return String.class;
        }
    };
    public static final Thing<Integer> Type2 = new Thing<Integer>() {
        @Override
        public Class<Integer> getCaste() {
            return Integer.class;
        }
    };

    private Thing() {
    }
}

如您所见,这不是enum。仅使用enum是不可能的,因为枚举不能包含类型参数。

p.s。:如果您觉得这有帮助,请查看Radiodef's answer以获得更完整的解释,毕竟我从他那里学到了这一点:)

答案 1 :(得分:2)

您可以保留未指定返回类的type参数:

public enum Thing implements HasCaste {

    Type1 {
        @Override
        public Class<String> getCaste() {
            return String.class;
        }
    }, Type2 {
        @Override
        public Class<Integer> getCaste() {
            return Integer.class;
        }
    };
}

interface HasCaste {
    public Class<?> getCaste();
}

答案 2 :(得分:1)

假设您想要定义几个不同的“类型”枚举常量,那么可以这样做:

interface HasCaste {
    public Class<?> getCaste();
}

public enum Thing implements HasCaste<?> {

    Type1(String.class),
    Type2(Integer.class);

    public final Class<?> clazz;

    private Thing(Class<?> clazz) {
        this.clazz = clazz;
    }

    @Override
    public Class<?> getCaste() {
        return clazz;
    }
}

然后一个人将打字延迟到将来使用getCaste。枚举的主要特征是封闭值域;必须列出类中所有可能的值。