Java: Casting from List to List when B implements A?

后端 未结 7 861
时光说笑
时光说笑 2020-11-29 13:01

I have the following class & interface defined:

public interface A {
}

public class B implements A {
}

I have a List of <

相关标签:
7条回答
  • 2020-11-29 13:05
    List<A> listA = (List<A>)(List<?>) listB;
    

    not recommended.

    0 讨论(0)
  • 2020-11-29 13:18

    I'm sure you need make the whole list List< A >(weird parsing there) and when adding new B objects cast them with (A)

    listA.add( (A) new B());  // dummy data
    
    0 讨论(0)
  • 2020-11-29 13:18

    It is just a matter of declarations. Don't declare listB as List but as List or List.

    List<A> listB = new List<B>();
    listB.add(new B());  // dummy data
    listB.add(new B());  // dummy data
    listB.add(new B()); // dummy data
    
    List<A> listA = listB;
    

    As simple as that. If you want to force listB to be List (avoiding the addition of any non-B element) you will be forced to use:

    List<A> listA = new ArrayList<A>(listB);
    

    But as they already pointed out, if you are forced to do that it is not a good sign.

    0 讨论(0)
  • 2020-11-29 13:20

    We can achieve this using Generics and Wildcards. You might not be able to create List<A> but create something like List<? extends A> which will call all the methods of the interface which is enough for most I think.

    Creating a new collection is expensive and not advisable. Since the references of the same objects will be passed on into the new collection, the additional list creation step is just an overhead.

    List<B> bList = new ArrayList<B>();
    
    List<? extends A> aList = bList;
    
    0 讨论(0)
  • 2020-11-29 13:26

    You cannot cast it like that. Create a new one:

    List<A> listA = new ArrayList<A>(listB);
    

    The constructor takes Collection<? extends A>. It will point to the same references anyway.

    0 讨论(0)
  • 2020-11-29 13:28

    Rather than fighting against a language feature, you should learn to use it properly.

    Rather than asking how to use unsafe casts to work around the error, it is instructive to first understand why there's an error; why what you're asking to do is unsafe (because you can add an A to the list using listA and then take it out of the list as a B using listB).

    Then, you should explain why you think that your use case does not run into the unsafe scenario. Because the answer to this will give a hint for how to change your code to make it work correctly with generics.

    • If you say that it is not unsafe because you never add anything using listA, then you should change the type of listA to List<? extends A>. That way, you can assign listB to it directly without any casts, and you won't be able to add anything to it using listA (except null).
    • If you say that it is not unsafe because you never get anything out using listB, then why not change the type of listB to List<A> in the first place?
    0 讨论(0)
提交回复
热议问题