Есть абстрактная структура, которая коде представлена тремя переменными: long, int[], double[]. Каким образом правильнее всего записать данные в ByteBuffer? Проблема возникла из-за того, что такие методы как ByteBuffer::asDoubleBuffer() создают вид, которые при записи не обновляет position исходного буфера. Проще говоря, следующий код некорректен:
public void write(WritableChannel channel, long a, int[] b, double[] c) {
ByteBuffer buffer = ByteBuffer.allocate(BIG_ENOUGH);
buffer.putLong(a);
buffer.asIntBuffer().put(b); // не обновит buffer.position
buffer.asDoubleBuffer().put(c) // аналогично
buffer.flip(); // установит limit = 8
channel.write(buffer); // запишет только 'a'
}
Решения:
1. Можно вручную установить значение position вызовом ByteBuffer::position(int).
2. Можно использовать ByteBuffer::wrap(), оборачивая один и тот же byte[] со смещением:
byte[] buffer = new byte[BIG_ENOUGH];
ByteBuffer.wrap(buffer).putLong(a);
ByteBuffer.wrap(buffer, Long.BYTES, BIG_ENOUGH - Long.BYTES).asIntBuffer().put(b);
...
В последнем случае значение position нам неважно, потому что в конце мы вызовем:
channel.write(ByteBuffer.wrap(buffer))
Очевидно, что и так, и так можно допустить глупые ошибки, и вообще смысд использования ByteBuffer (и nio) пропадает. Как бы сделали вы?