2010-09-17 4 views
44

Мне нужно преобразовать объекты в байт [], которые будут храниться в хранилище ключей для магазина Tokyo Cabinet. Мне также нужно удалить байт [] в объект при чтении из хранилища значений ключа.Java: объект для байта [] и байт [] для конвертера объектов (для Tokyo Cabinet)

Есть ли какие-либо пакеты, которые помогут мне с этой задачей? Или самое лучшее решение для его реализации?

+2

Сделайте свой класс [Serializable] (http://download.oracle.com/javase/6/docs/api/java/io/Serializable.html), затем используйте ответ в [ Java Serializable Object to Byte Array ] (http://stackoverflow.com/questions/2836646/java-serializable-object-to-byte-array). –

+0

это не точный дубликат, хотя он выглядит так – Bozho

ответ

119
public static byte[] serialize(Object obj) throws IOException { 
    ByteArrayOutputStream out = new ByteArrayOutputStream(); 
    ObjectOutputStream os = new ObjectOutputStream(out); 
    os.writeObject(obj); 
    return out.toByteArray(); 
} 
public static Object deserialize(byte[] data) throws IOException, ClassNotFoundException { 
    ByteArrayInputStream in = new ByteArrayInputStream(data); 
    ObjectInputStream is = new ObjectInputStream(in); 
    return is.readObject(); 
} 
+0

не забудьте вызвать 'is.close' и' in.close'. –

+16

'is.close' и' in.close' в этом случае не нужны, потому что это поток в памяти. Единственное, что он сделал бы здесь, это сделать его более медленным и более подробным. Но я понимаю, что IDE может помечать код выше, потому что поток не закрыт. –

+3

Я не думаю, что это будет медленнее, это всего лишь пустой метод, поэтому разница во времени должна быть очень низкой. Но вы правы: «Закрытие ByteArrayOutputStream не имеет эффекта». [Java Doc] (http://docs.oracle.com/javase/6/docs/api/java/io/ByteArrayOutputStream.html#close%28%29) Awesome: D –

9

Если ваш класс расширяет Serializable, вы можете писать и читать объекты через ByteArrayOutputStream, это то, что я обычно делаю.

+3

Все типы, включенные как переменные в вашем классе (и все типы в этих типах и т. Д.), Также должны быть Serializable. –

+0

На самом деле ему понадобится ObjectOutputStream, чтобы обернуть BAOS тоже ... Но да, это самый простой способ. –

+0

Я бы подумал об использовании чего-то другого, кроме встроенной сериализации Java, также - сериализации JBoss, JSerial, Avro и т. Д. Или XML-формата, такого как XStream или Javolution marshalling plus gzip. Стандартная сериализация не особенно быстро, и хотя ее предельная эффективность пространства хороша, накладные расходы для каждого потока довольно много. –

5

Вы можете посмотреть, как Гектор делает это для Cassandra, где цель одна и та же - конвертировать все в byte[], чтобы хранить/извлекать из базы данных NoSQL - see here. Для примитивных типов (+ String) существуют специальные Сериализаторы, в противном случае существует общий ObjectSerializer (ожидается Serializable и с использованием ObjectOutputStream). Разумеется, вы можете использовать его только для всего, но в сериализованной форме могут быть избыточные метаданные.

Я думаю, вы можете скопировать весь пакет и использовать его.