Java Автоматическая Сериализация Значения Поля - PullRequest
2 голосов
/ 17 февраля 2012

Допустим, у нас есть Java-класс struct-llike

public class Person {
    private int height;
    private byte nChildren;
    private int  salary; 

    public byte[] serializeField() {
        ByteBuffer buf = ByteBuffer.allocate(4 + 1 + 4);
        buf.order(ByteOrder.BIG_ENDIAN);
        buf.putInt(height);
        buf.put(nChildren);
        buf.putInt(salary);
        return buf.array(); 
    }

    /*
     * setters and getters
     */
}

Существует ли библиотека, которая может автоматически выполнять функцию serializeField() для любого данного класса?Он должен иметь возможность поддерживать точный порядок полей, определенных в классе, и, возможно, иметь возможность игнорировать определенные поля (например, serialVersionUID).

1 Ответ

0 голосов
/ 17 февраля 2012

Вы можете написать один, используя отражение.

Если производительность имеет значение, вы можете

  • передайте ByteBuffer для добавления, чтобы избежать создания большого количества буферов, которые вы отбрасываете.

    public void serializeField(ByteBuffer buf) {
        buf.putInt(height);
        buf.put(nChildren);
        buf.putInt(salary);
    }
    
  • и сгенерируйте свой код (используя отражение и т. Д.), Чтобы избежать использования отражения во время выполнения. то есть используйте отражение для генерации кода выше или в следующем примере.

  • отображает методы получения и установки полей в ByteBuffer, поэтому сериализация / десериализация как таковая отсутствует.

Скажем, у вас есть объект с шириной и высотой. Как вы можете видеть, значения обновляются в ByteBuffer (например, файл с прямым отображением или с отображением в памяти). Таким образом, нет никаких издержек сериализации как таковых.

class Sized {
    private ByteBuffer buffer;
    private static final int HEIGHT_OFFSET = 0;
    private static final int WIDTH_OFFSET = 4;

    public void setBuffer(ByteBuffer buffer) {this.buffer = buffer; }
    public int getHeight() { return buffer.getInt(HEIGHT_OFFSET); }
    public void setHeight(int height) { buffer.putInt(HEIGHT_OFFSET, height); }
    public int getWidth() { return buffer.getInt(WIDTH_OFFSET); }
    public void setWidth(int width) { buffer.putInt(WIDTH_OFFSET, width); }
}

Для обработки отображенных в памяти данных вы можете использовать такую ​​библиотеку.

https://github.com/peter-lawrey/Java-Chronicle

Эта библиотека позволяет вам создавать любое количество событий / записей (миллиарды), которые могут быть обновлены (но не увеличены в размере после записи) очень быстро. например миллионы записей в секунду с задержкой менее микросекунды. Это может также быть разделено между процессами. Когда вы превышаете объем основной памяти, основным ограничением является скорость вашего жесткого диска, если вы превышаете объем используемой памяти. то есть SSD действительно поможет. В нем есть режим, в котором вы используете класс Unsafe напрямую (более низкий уровень, чем ByteBuffer), просто включив его.

...