Add support for Table<R, C, V> #11
Description
The Guava Table<R, C, V>
data structure is a convenience wrapper around a Map<R, Map<C, V>>
. This form can be easily serialized and deserialized. Here's the basic code I'm using for that:
public static class TableSerializer extends JsonSerializer<Table<?, ?, ?>> {
@Override
public void serialize(final Table<?, ?, ?> value, final JsonGenerator jgen, final SerializerProvider provider) throws IOException,
JsonProcessingException {
jgen.writeObject(value.rowMap());
}
@Override
public Class<Table<?, ?, ?>> handledType() {
return (Class)Table.class;
}
} // end class TableSerializer
public static class TableDeserializer extends JsonDeserializer<Table<?, ?, ?>> {
@Override
public Table<?, ?, ?> deserialize(final JsonParser jp, final DeserializationContext ctxt) throws IOException, JsonProcessingException {
final ImmutableTable.Builder<Object, Object, Object> tableBuilder = ImmutableTable.builder();
final Map<Object, Map<Object, Object>> rowMap = jp.readValueAs(Map.class);
for (final Map.Entry<Object, Map<Object, Object>> rowEntry : rowMap.entrySet()) {
final Object rowKey = rowEntry.getKey();
for (final Map.Entry<Object, Object> cellEntry : rowEntry.getValue().entrySet()) {
final Object colKey = cellEntry.getKey();
final Object val = cellEntry.getValue();
tableBuilder.put(rowKey, colKey, val);
}
}
return tableBuilder.build();
}
} // end class TableDeserializer
I have not tested if this correctly supports contextual keys or type (de)serialization. I looked at MultimapSerializer
and MultimapDeserializer
, and they are much more complicated even though a Multimap<K, V>
is just a convenience wrapper around Map<K, Collection<V>>
, so maybe this is too simplistic?
Notably, this implementation always deserializes to an ImmutableTable
. Heuristics could be used to determine what Table
implementation to reconstruct, e.g., if every row, column value is non-null, could create ArrayTable
. HashBasedTable
would be a good mutable default.