1

I have

ByteBuffer buf = ByteBuffer.allocateDirect(500);

Then I use buf.put(byte) a couple of times, say 20. I save it to sql blob via the underlying array, i.e. by calling buf.array(). However, the length of buf.array() is 500. How to get an array (byte[]) of length 20 that can be passed to other (read-only) functions? (without copying, of course.)

3
  • Do you want to get the byte array of length 20 from a byte array of length 500 of from a buffer with capacity of 500 or do you not care how? Commented Mar 28, 2014 at 16:16
  • Do not care how. Just want the first 20 bytes of the underlying array of "buf", in a form of byte array with length 20. Since in the real life the 20 is more like 200000, I'd rather not do any copies. Commented Mar 28, 2014 at 16:27
  • 1
    With allocateDirect, the buffer does not have an underlying array. But even if it has an array, you can not get a portion of an array in Java in general. So there is no way of doing this without copies. If you have the possibility to change the receiving method, you could give it a bytebuffer.slice(), which is a view on a portion of the byte buffer (namely, the portion between its current position and limit - which you can set accordingly before calling slice), or alternatively, let it receive the full byte[], an int position and an int length (which is done often) Commented Mar 28, 2014 at 16:46

1 Answer 1

4

try this

ByteBuffer buf = ByteBuffer.allocate(500);
buf.putInt(1);
...
...
byte[] a = new byte[buf.position()];
buf.rewind();
buf.get(a);
Sign up to request clarification or add additional context in comments.

4 Comments

Just to make sure I understand this, is "a" here just a view of the original buffer? i.e. are "new byte[buf.position()]" and "buf.get(a)" both O(1) operations and no copy is performed?
it's a copy operation but there is no other solution
True. You have a buffer and you want to create an array, the new array must have its content copied from the buffer since you can't transform a buffer into an array. You might save yourself some workload using: A byte buffer is either direct or non-direct. Given a direct byte buffer, the Java virtual machine will make a best effort to perform native I/O operations directly upon it. That is, it will attempt to avoid copying the buffer's content to (or from) an intermediate buffer before (or after) each invocation of one of the underlying operating system's native I/O operations.
@EvgeniyDorofeev Ok, then this should work, thanks. One also needs to call "buf.position(0)" between the lines "byte[] a = new ..." and "buf.get(a);" to get it from the start.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.