为什么我不能在覆盖方法中添加类型参数?

问题描述 投票:0回答:1

我需要在我的子类中实现一种方法

Foo

Bar
您可以看到,我的方法将从类型参数中受益:

class Foo { public abstract void foo(); } class Bar extends Foo { private <T> Map<T, List<T>> getStuff() { ... } @Override public void foo() { Map<?, List<?>> stuff = getStuff(); for (Entry<?, List<?>> e : stuff.entrySet()) { Object key = e.getKey(); List<?> lst= e.getValue(); lst.add(key); // illegal: need ?, got Object } } }
(我也可以使用RAW类型,因为我知道它会起作用,但是我读过的所有内容都说您不应该这样做)

不幸的是,这是非法的 - 我的方法@Override public <T> void foo() { Map<T, List<T>> stuff = getStuff(); for (Entry<T, List<T>> e : stuff.entrySet()) { T key = e.getKey(); List<T> lst= e.getValue(); lst.add(key); // legal! } }

foo

中与foo()在foo中发生冲突;这两种方法都具有相同的擦除,但都没有覆盖对方”。 this this Gook,鉴于我的类型参数不会更改参数或返回类型。

我的解决方法的丑陋hack直到现在,只需写一个全新的(参数化)方法:
Bar

我有两个问题:

为什么将类型参数添加到方法中,以防止其超级类中的未参数化方法?
有一种更好的方法来获得我想要的行为?
	

请参见

JLS8.4.2


8.4.2。方法签名

    两个方法或构造函数,M和N,如果它们具有相同的名称,则具有相同的签名,相同的类型参数(如果有)(如果有)(§8.4.4),以及在将N的正式参数类型调整为M的类型参数后,则具有相同的正式参数类型。
  1. 方法M1的签名是方法M2的签名的子签名,如果是:
  2. M2具有与M1相同的签名 M1的签名与M2的签名的擦除(第4.6节)相同。
如果M1是M2或M2的子签名,则两种方法签名M1和M2是替代等值的。
java generics inheritance
1个回答
1
投票
由于类型参数是方法签名的一部分,您无法在覆盖方法中添加或删除类型参数。

我的解决方法的丑陋骇客... 是的,这很丑陋,但这是正确的方法。

foo

上面的答案很棒,只想添加一个小附录,从技术上讲,一个可以在覆盖方法中tope type type参数。我没有足够的声誉发表评论,所以我在这里写作

最新问题
© www.soinside.com 2019 - 2025. All rights reserved.