2012-06-19 4 views
3

Какой самый быстрый способ заполнить предварительно выделенный ByteBuffer в Java?Java ByteBuffer Put vs wrap

Я сначала задал размер ByteBuffer с «allocirect», это нужно сделать только один раз. После того, как я буду заполнять его непрерывно (перерабатывая его) как можно быстрее, с новыми данными, которые поступают в виде массива byte [], примерно каждые 5 мс и без использования памяти, поскольку я уже предварительно назначил ByteBuffer. В настоящее время я использую инструкцию «.put()», которая в моей системе занимает около 100 мс для завершения. Есть ли другой способ заполнить ByteBuffer? Функция «.wrap()» работает быстрее, не перераспределяя массив?

+0

Вы можете попробовать System.arraycopy. Проверьте: [лучше ли использовать System.arraycopy (...), чем цикл for для копирования массивов?] (Http://stackoverflow.com/questions/18638743/is-it-better-to-use-system-arraycopy -than-a-for-loop-for-copying-arrays) – user3668129

ответ

7

Я надеюсь, что вы имели в виду byte[] не Byte[]

put() это самый быстрый способ скопировать байт [] в ByteBuffer. Еще более быстрый способ - записать в ByteBuffer в первую очередь и не использовать byte[].

Если копия занимает 100 мс, возможно, вы копируете слишком много данных. В этом тесте он копирует 1 МБ за 128 микросекунд.

ByteBuffer bb = ByteBuffer.allocateDirect(1024 * 1024); 
byte[] bytes = new byte[bb.capacity()]; 

int runs = 50000; 
long start = System.nanoTime(); 
for (int i = 0; i < runs; i++) { 
    bb.clear(); 
    bb.put(bytes); 
} 
long time = System.nanoTime() - start; 
System.out.printf("Average time to copy 1 MB was %.1f us%n", time/runs/1e3); 

печатает

Average time to copy 1 MB was 128.9 us 
+0

К сожалению, я имел в виду байт []. Таким образом, единственный способ быстро заполнить ByteBuffer, самый быстрый способ, - это использовать «.put (...)»? Данные, которые я должен заполнить в каждом цикле, как и в вашем тесте, составляют около 1 МБ, которые я не могу обойти или уменьшить. – PerracoLabs

+0

Вы уверены, что его 100 мс, а не 100 микросекунд? Если вы не можете уменьшить его, лучшим решением является вовсе не использовать байт [] и иметь то, что когда-либо создает эту запись непосредственно в ByteBuffer. –

+0

да, это занимает около 100 мс. К сожалению, данные, полученные из аппаратного обратного вызова, поступают в виде массива byte [], и последняя команда, которая должна обрабатывать его, принимает только ByteBuffer, который также я не могу изменить. Поэтому я должен найти самый быстрый способ скопировать эти данные и без повторного выделения памяти все время. – PerracoLabs

0

обертывание должна быть намного быстрее, так как --Если я понимаю документ correctly-- не копирует массив байтов, а просто устанавливает переменные-члены (емкость/предел/положение). обертка имеет смысл, если вы уже получили байт [] с желаемыми данными откуда-то, конечно.