Whats the best to way convert a set of Java objects to another set of objects?
Basic Java question here from a real newbie. I have a set of Java objects (of class "MyClass") that implement a certain interface (Interface "MyIfc"). I have a set of these objects stored in a private variable in my class that is declared as follows:
protected Set<MyClass> stuff = new HashSet<MyClass>();
I need to provide a public method that returns this set as a collection of objects of type "MyIfc".
public Collection<MyIfc> getMyStuff() {...}
How do I do the conversion? The following line gives me an error that it can't do the conversion. I would have guessed the compiler knew that objects of class MyClass implemented MyIfc and therefore would have handled it.
Collection<MyI开发者_StackOverflow中文版fc> newstuff = stuff;
Any enlightenment is appreciated.
Probably the most correct way is:
return new HashSet<MyIfc>(stuff);
If the class is too large to do that, you can do:
return Collections.unmodifiableSet(stuff);
The compiler doesn't like your assignment of stuff to newstuff, because it lays open the possibility of putting things in newstuff that implement MyIfc but are not of type MyClass. You could have your getter create its own collection:
public Collection<MyIfc> getMyStuff() {
Collection<MyIfc> coll = new HashSet<MyIfc>();
coll.addAll(myStuff);
return coll;
}
You don't need to do any conversion. You will have to type your stuff
as Set<MyIfc>
.
Background: Yes, it is correct that if you have an object of type MyClass
this will also be usable as a MyIfc
instance. But you explicitly typed your Set as of type MyClass
. And this is simply something different than a Set of type MyIfc
. After all, you could also have other classes that implement MyIfc
and then you could also put them into your Set<MyIfc>
but not into Set<MyClass>
.
Google collections define a bunch of lazy adapters, that may be suitable for your purposes.
One in particular is Collections2.transform. Here is an example on how to adapt your collection:
Collection<MyIfc> newStuff =
Collections2.transform(
stuff,
new Function<MyClass, MyIfc>( )
{
public MyIfc apply ( final MyClass from )
{
return (MyIfc) from; // This may throw a ClassCastException though
}
}
)
精彩评论