How to assign a List<ClassB> to a setter which takes List<ClassA> and ClassB extends ClassA
I have something like
public void setCustomHandler(final List<ClassA> customHandler) {
this.customHandler = customHandler;
}
Now I create a classB and call setCustomHandler(List<B>)
. Eclipse is telling me to create
setCustomHandler(final List<ClassB> customHandler){
}
Ho开发者_如何学运维w can I just assign
List<ClassB objects> to List<ClassA objects>?
Short answer: You can't.
List<ClassB>
is not a subtype of List<ClassA>
(even if ClassB
is a subtype of ClassA
):
List<ClassA> handlerList;
List<ClassB> bHandlers = new ArrayList<ClassB>();
handlerList = bHandlers; // Type mismatch: cannot convert from
// List<ClassB> to List<ClassA>
If you have the control of the receiving class, you could perhaps let it accept List<? extends ClassA>
instead:
List<? extends ClassA> handlerList;
List<ClassB> bHandlers = new ArrayList<ClassB>();
handlerList = bHandlers; // Compiles fine.
setCustomHandler(final List<? extends ClassA> customHandler){
}
That was the short answer, the long answer is: depends waht you want to do in setCustomHandler()
. If you want to get from the list, that that works, but if you want to put in the list, it wont work. The reason is: List<? extends ClassA> customHandler
says that customHandler
contains some subtype of ClassA, but you don't know which one, which prevents you to add
(you do not know what is in the list).
If you want to put in the list you have to do
setCustomHandler(final List<? super ClassA> customHandler){
}
which says that customHandler
contains some supertype of ClassA. This allows you to put ClassB, but does not allow get.
Effective Java from Bloch and The Java Programming Language from Arnold explain all these things in deatil.
You can't. That's what generics is there to prevent.
You can create a List<ClassA>
and the set the object of ClassB
, as the reference variable will be of type ClassA
, then u can call the method you need to call.
List<ClassA> list = new ArrayList<ClassA>();
ClassA object = new ClassB();
list.add(object);
setCustomerHandler(list);
This will help you.
If ClassA and ClassB have no relation then you can't. If they are in the same hierarchy structure (suppose both inherits from ClassC) put a parent class reference (ClassC).
For example:
public ClassC{}
public ClassA<T extends ClassC> extends ClassC{
public void setCustomHandler(final List<T> customHandler) {
this.customHandler = customHandler;
}
}
I don't remember much java but I believe it is something like that :
Create a List<ClassA>
and add all your ClassB items to it like this :
List<ClassA> myList = new List<ClassA>();
myList.addAll(myListOfOtherItems);
Now you can use myList to call your method since it's of type List<ClassA>
but contains ClassB items that extends ClassA
The problem you are facing is that while ClassA
and ClassB
have a specific relationship, List<ClassA>
and List<ClassB>
do not have one.
You cannot assign, instead you have to insert the elements in the first list to the second list one-by-one.
You can't.
You can use wildcard ?
,
void setCustomHandler(final List<?> customHandler)
But you will have to find out the parameterized type somehow.
精彩评论