Использование динамических буферов?Джава - PullRequest
4 голосов
/ 01 марта 2011

В Java у меня есть метод

public int getNextFrame( byte[] buff )

, который читает из файла в буфер и возвращает количество прочитанных байтов. Я читаю из .MJPEG, который имеет 5-байтовое значение, скажем, «07939», а затем столько байтов для jpeg.

Проблема в том, что размер байта JPEG может переполнить буфер Я не могу найти аккуратное решение для распределения. Моя цель - не создавать новый буфер для каждого изображения. Я попробовал прямой ByteBuffer, чтобы я мог использовать его метод array(), чтобы получить прямой доступ к базовому буферу. ByteBuffer не расширяется динамически.

Должен ли я возвращать ссылку на параметр? Как:

public ByteBuffer getNextFrame( ByteBuffer ref )

Как найти прочитанные байты? Спасибо.

Ответы [ 4 ]

1 голос
/ 01 марта 2011

Просто прочитайте необходимое количество байтов.Не используйте read(buffer), но используйте read(buffer,0,size).Если есть еще байты, просто отбросьте их, JPG все равно будет поврежден.

1 голос
/ 01 марта 2011

java.io.ByteArrayOutputStream - это обертка вокруг массива байтов, увеличивающая ее по мере необходимости.Возможно, это то, что вы могли бы использовать.

Редактировать:
Для повторного использования просто позвоните reset () и начните сначала ...

0 голосов
/ 01 марта 2011

Обычный способ выполнить это в высокоуровневом API - это либо позволить пользователю предоставить OutputStream и заполнить его вашими данными (которые могут быть ByteArrayOutputStream или чем-то совершенно иным), либо иметь InputStream в качестве возвращаемое значение, которое пользователь может прочитать, чтобы получить данные (которые будут динамически загружать правильные детали из файла и останавливаться после завершения).

0 голосов
/ 01 марта 2011

РЕДАКТИРОВАТЬ:

Выделение байта [] намного быстрее, чем чтение из файла или сокет, я был бы удивлен, это будет иметь большое значение, если вы есть система, где микросекунды стоят денег.

Время чтения файла размером 64 КБ составляет около 10 мс (если файл находится в памяти)

Время, выделяемое для байта размером 64 КБ [], составляет около 0,001 мс, возможно быстрее.


Вы можете использовать IOBuffer в Apache IO, однако это очень дорого расширяется.

Вы также можете использовать ByteBuffer, position() сообщит вам, сколько данных было прочитано.

Если вы не знаете, насколько большим будет буфер, и у вас есть 64-битная JVM, вы можете создать большой прямой буфер. Это будет выделять память (постранично) только при использовании. В результате вы можете выделить 1 ГБ, но можете использовать только 4 КБ, если это все, что вам нужно. Прямой буфер не поддерживает array(), однако вам придется читать из ByteBuffer, используя другие методы.

Другим решением является использование AtomicReference<byte[]>, вызываемый метод может увеличивать размер по мере необходимости, но если он будет достаточно большим, он будет использовать предыдущий буфер.

...