Reputation: 101
Overview, I have an abstract class from which three concrete classes inherit.
public abstract class A {}
public class B extends A {}
public class C extends A {}
public class D extends A {
private List<A> children;
}
Main point is that concrete class D has a list that could contain objects of concrete class B, C or D.
My challenge is how to serialize D given that its children could be of three different types; itself or the two other concrete classes. I have a working custom serializer that works if all the children are of the same type. Not looking for a full blown solution, a high level approach or strategy will be fine. Thanks.
Upvotes: 2
Views: 1063
Reputation: 4496
Take a look to https://stackoverflow.com/a/22081826/3315914. There's a working example of it. All you need is Gson's RuntimeTypeAdapterFactory. A simple example could be:
RuntimeTypeAdapter<Shape> shapeAdapter = RuntimeTypeAdapterFactory.of(Shape.class)
.registerSubtype(Rectangle.class)
.registerSubtype(Circle.class)
.registerSubtype(Diamond.class);
And then,
Gson gson = new GsonBuilder()
.registerTypeAdapter(Shape.class, shapeAdapter)
.create();
Also, here you can also find a similar answer.
I hope it helps.
Upvotes: 1
Reputation: 76898
I highly suspect you are using some ancient version of Gson
or you're not explaining exactly what the problem is. Using v2.2.4 of Gson:
public class App
{
public static void main(String[] args)
{
D d = new D();
D d2 = new D();
d.list.add(d2);
System.out.println(new Gson().toJson(d));
}
}
abstract class A
{
private int a = 5;
}
class B extends A
{
private int b = 6;
}
class C extends A
{
private int c = 7;
}
class D extends A
{
List<A> list = new ArrayList<A>();
public D()
{
list.add(new B());
list.add(new C());
}
}
Output:
{"list":[{"b":6,"a":5},{"c":7,"a":5},{"list":[{"b":6,"a":5},{"c":7,"a":5}],"a":5}],"a":5}
As you can see, the inherited private field a
from the abstract A
is serialized correctly when B
,C
, and D
are serialized.
Upvotes: 0