我想为Ehcache的Optional类编写序列化程序。我知道,可选成员是可连接的,所以我写道:
@Override
public ByteBuffer serialize(Optional object) throws SerializerException {
if( object.isPresent() ) {
try {
ByteArrayOutputStream baos = new ByteArrayOutputStream();
ObjectOutputStream oos = new ObjectOutputStream(baos);
oos.writeObject(object);
return ByteBuffer.wrap(baos.toByteArray()); // excess copying
} catch (IOException e) {
throw new AssertionError(e);
}
}
else {
return ByteBuffer.wrap(new byte[] {});
}
}
@Override
public Optional read(ByteBuffer binary) throws ClassNotFoundException, SerializerException {
if( binary.array().length > 0 ) {
try {
byte[] buf = binary.array();
ByteArrayInputStream bais = new ByteArrayInputStream(buf);
ObjectInputStream ois = new ObjectInputStream(bais);
Object object = ois.readObject();
return Optional.of(object);
} catch (IOException e) {
throw new AssertionError(e);
}
}
else {
return Optional.empty();
}
}
我对评论行感到困惑,其中包括过多的数据复制。我可以避免使用ByteBuffer直接序列化吗?
虽然基于ByteBuffer的Ehcache seriazliers?
答案 0 :(得分:0)
ByteBuffer.wrap()
实际上并不复制数据。顾名思义它包装了数组,因此对原始数组的任何更改也会反映在缓冲区中。
答案 1 :(得分:0)
可悲的是,你不能在ByteBuffer上进行Java序列化。你正在做与Ehcache的内置PlainJavaSerializer
相同的事情。
顺便说一下,你可以通过这样做删除很多代码:
public class OptionalSerializer<T> implements Serializer<Optional<T>> {
private final PlainJavaSerializer<T> serializer;
public OptionalSerializer(ClassLoader classLoader) {
serializer = new PlainJavaSerializer<>(classLoader);
}
@Override
public ByteBuffer serialize(Optional<T> object) throws SerializerException {
return object.map(serializer::serialize).orElse(ByteBuffer.allocate(0));
}
@Override
public Optional<T> read (ByteBuffer binary) throws ClassNotFoundException, SerializerException {
if(binary.array().length > 0) {
return Optional.of(serializer.read(binary));
}
return Optional.empty();
}
@Override
public boolean equals(Optional<T> object, ByteBuffer binary) throws ClassNotFoundException, SerializerException {
return object.equals(read(binary));
}
}