Java中忽略泛型
所以我有以下Java代码:Java中忽略泛型,java,generics,Java,Generics,所以我有以下Java代码: public <A extends Action> List<A> getActionsFor(Actor a) { List<A> theActions = super.getActionsFor(a); for (Action ac: a.getItemCarried().getActions()) { theActions.add(ac); } return theActio
public <A extends Action> List<A> getActionsFor(Actor a) {
List<A> theActions = super.getActionsFor(a);
for (Action ac: a.getItemCarried().getActions()) {
theActions.add(ac);
}
return theActions;
}
public List getactions for(参与者a){
列出操作=super.getActions for(a);
对于(操作ac:a.getItemCarried().getActions()){
添加(ac);
}
返回动作;
}
出于某种原因,javac拒绝了.add(ac)声明add(A)不能应用于操作
我是不是丢了什么钥匙?我可以通过在两个包之间创建依赖项来解决这个问题,但我真的不想这样做
所有有问题的类都已正确导入,每个方法调用都有效,所以我真的不明白为什么它不能接受A扩展的类类型
如果您有任何建议,即使您不确定,我们也将不胜感激,因为我必须在接下来的6小时内修复此问题,否则我将需要创建依赖项。您正在声明一个明确的
A
列表,如果您要接受所有子类,请在列表声明中指定:
List<? extends A> theActions = super.getActionsFor(a);
List在您的示例中,您没有指定什么是A
,它是Action
的子类。您想添加一个不允许的超类型a
(一个操作
)的实例。您需要强制转换到A
(不安全,会发出警告),或者只返回列表
我是不是丢了什么钥匙
A
是扩展动作的东西,ac
也是扩展动作的东西。然而,这有点像设施
Yesterday I saw someone.
Someone is the President
Therefor, yesterday I was the President.
问题是编译器无法知道A
和Action
是Action
的兼容子类
一个简单的解决办法是不要太具体。在此方法中使用Action
而不是A
public List<Action> getActionsFor(Actor a) {
// this has to return a copy of the List or you will be modifying an original
List<Action> theActions = super.getActionsFor(a);
for (Action ac: a.getItemCarried().getActions()) {
theActions.add(ac); // ac is an Action so all good.
}
return theActions;
}
public List getactions for(参与者a){
//这必须返回列表的副本,否则您将修改原始列表
列出操作=super.getActions for(a);
对于(操作ac:a.getItemCarried().getActions()){
theActions.add(ac);//ac是一个非常好的动作。
}
返回动作;
}
或者你可以做你所拥有的,但更复杂
public <A extends Action> List<A> getActionsFor(Actor<A> a) {
List<A> theActions = super.getActionsFor(a);
for (A ac: a.getItemCarried().getActions()) {
theActions.add(ac); // ac is an A, so all good.
}
return theActions;
}
public List getactions for(参与者a){
列出操作=super.getActions for(a);
对于(A ac:A.getItemCarried().getActions()){
theActions.add(ac);//ac是A,所以一切都好。
}
返回动作;
}
如果将
用作泛型类型,则不能以类型安全的方式将元素添加到使用a
键入的列表中
原因是您不知道A
的确切类型
假设您有两个子类Action
:ActionA
和ActionB
现在完全可以这样写:
List<A> theActions = new ArrayList<ActionA>();
那么,我如何让它接受“行动”呢?”A“应该已经采取了任何类型的“Action”或从“Action”扩展而来的东西,不是吗?我已经把我的评论移到了一个答案上,并扩展了我要补充的一点:泛型类型没有你可能期望的那种超/子类关系。例如,ArrayList
不是ArrayList
的超类型。为什么?如果ArrayList
是ArrayList
的超类型,则可以执行ArrayList list=new ArrayList()
,然后您可以将编号
对象放入列表
,这应该是一个数组列表这不允许您添加(),只允许获取()啊,是的,您是对的。在这种情况下,我认为您的答案更正确。您提供的第二个解决方案返回完全相同的错误,但第一个解决方案确实有效。这真的让我很困惑,因为超级类中存在几乎相同的代码,引用不同的类,但具有相同的关系,并且在那里工作得很好。感谢您的帮助。@David第二种方法只有在getActions()
返回列表时才有效。
注意:Actor
还有更多的更改要使其工作。
theActions.add(new Action()); // doesn't compile