使用这部iphone重设您的apple id密码_bytebuffer.get

大家好,又见面了,我是你们的朋友全栈君。

文章目录

ByteBuffer类提供了6类操作。

  1. 以绝对位置和相对位置读写单个字节的get()和put()方法
  2. 使用相对批量get(byte[] dst)方法可以将缓冲区中的连续字节传输到byte[] dst目标数组中。
  3. 使用相对批量put(byte[] src)方法可以将byte[]数组或其他字节缓冲区中的连续字节存储到此缓冲区中。
  4. 使用相对和绝对getType和putType方法可以按照字节顺序在字节序列中读写其他基本数据类型的值,方法getType和putType可以进行数据类型的自动转换。
  5. 提供了创建视图缓冲区的方法,这些方法允许将字节缓冲区视为包含其他基本类型值的缓冲区,这些方法有asCharBuffer()、asDoubleBuffer()、asFloatBuffer()、asIntBuffer()、asLongBuffer()、asShortBuffer()。
  6. 提供了对字节缓冲区进行压缩(compacting)、复制(duplicating)和截取(slicing)的方法。

创建堆缓冲区和直接缓冲区

字节缓冲区分为直接字节缓冲区(JVM会尽量直接对内核空间进行IO操作,避免将缓冲区内容复制到中间缓冲区,提高效率)和非直接字节缓冲区。 allocateDirect()创建直接字节缓冲区,通过工厂方法allocateDirect()返回的缓冲区进行内存的分配和释放所需要的时间成本通常要高于非直接缓冲区。

allocate源码:

/**
     * Allocates a new direct byte buffer.
     *
     * <p> The new buffer's position will be zero, its limit will be its
     * capacity, its mark will be undefined, and each of its elements will be
     * initialized to zero.  Whether or not it has a
     * {@link #hasArray backing array} is unspecified.
     *
     * @param  capacity
     *         The new buffer's capacity, in bytes
     *
     * @return  The new byte buffer
     *
     * @throws  IllegalArgumentException
     *          If the <tt>capacity</tt> is a negative integer
     */
    public static ByteBuffer allocateDirect(int capacity) {
        return new DirectByteBuffer(capacity);
    }
    
    /**
     * Allocates a new byte buffer.
     *
     * <p> The new buffer's position will be zero, its limit will be its
     * capacity, its mark will be undefined, and each of its elements will be
     * initialized to zero.  It will have a {@link #array backing array},
     * and its {@link #arrayOffset array offset} will be zero.
     *
     * @param  capacity
     *         The new buffer's capacity, in bytes
     *
     * @return  The new byte buffer
     *
     * @throws  IllegalArgumentException
     *          If the <tt>capacity</tt> is a negative integer
     */
    public static ByteBuffer allocate(int capacity) {
        if (capacity < 0)
            throw new IllegalArgumentException();
        return new HeapByteBuffer(capacity, capacity);
    }

直接缓冲区与非直接缓冲区运行效率比较

long begin = System.currentTimeMillis();
ByteBuffer buffer = ByteBuffer.allocateDirect(1000000000);
for (int i = 0; i < 1000000000; i++) {
    buffer.put((byte)100);
}
System.out.println(System.currentTimeMillis() - begin);

output:
	1896
long begin = System.currentTimeMillis();
ByteBuffer buffer = ByteBuffer.allocate(1000000000);
 for (int i = 0; i < 1000000000; i++) {
     buffer.put((byte)100);
 }
 System.out.println(System.currentTimeMillis() - begin);

output:
	2575

直接缓冲区运行效率要高些。直接缓冲区(DIrectByteBuffer)内部使用sun.misc.Unsafe类进行值的处理。Unsafe的作用是JVM与操作系统进行直接通信,提高程序运行的效率。

public ByteBuffer put(byte x) {
        unsafe.putByte(ix(nextPutIndex()), ((x)));
        return this;
}

非直接缓冲区(HeapByteBuffer)在内部直接对byte[] hb字节数组进行操作,而且还是在JVM的堆中进行数据处理,运行效率相对慢些。

public ByteBuffer put(byte x) {
        hb[ix(nextPutIndex())] = x;
        return this;
 }

包装wrap数据的处理

wrap(byte[] array):

/**
     * Wraps a byte array into a buffer.
     *
     * <p> The new buffer will be backed by the given byte array;
     * that is, modifications to the buffer will cause the array to be modified
     * and vice versa.  The new buffer's capacity and limit will be
     * <tt>array.length</tt>, its position will be zero, and its mark will be
     * undefined.  Its {@link #array backing array} will be the
     * given array, and its {@link #arrayOffset array offset>} will
     * be zero.  </p>
     *
     * @param  array
     *         The array that will back this buffer
     *
     * @return  The new byte buffer
     */
    public static ByteBuffer wrap(byte[] array) {
        return wrap(array, 0, array.length);
    }

wrap(byte[] array, int offset, int length):

 /**
     * Wraps a byte array into a buffer.
     *
     * <p> The new buffer will be backed by the given byte array;
     * that is, modifications to the buffer will cause the array to be modified
     * and vice versa.  The new buffer's capacity will be
     * <tt>array.length</tt>, its position will be <tt>offset</tt>, its limit
     * will be <tt>offset + length</tt>, and its mark will be undefined.  Its
     * {@link #array backing array} will be the given array, and
     * its {@link #arrayOffset array offset} will be zero.  </p>
     *
     * @param  array
     *         The array that will back the new buffer
     *
     * @param  offset
     *         The offset of the subarray to be used; must be non-negative and
     *         no larger than <tt>array.length</tt>.  The new buffer's position
     *         will be set to this value.
     *
     * @param  length
     *         The length of the subarray to be used;
     *         must be non-negative and no larger than
     *         <tt>array.length - offset</tt>.
     *         The new buffer's limit will be set to <tt>offset + length</tt>.
     *
     * @return  The new byte buffer
     *
     * @throws  IndexOutOfBoundsException
     *          If the preconditions on the <tt>offset</tt> and <tt>length</tt>
     *          parameters do not hold
     */
    public static ByteBuffer wrap(byte[] array, int offset, int length)
    {
        try {
            return new HeapByteBuffer(array, offset, length);
        } catch (IllegalArgumentException x) {
            throw new IndexOutOfBoundsException();
        }
    }

注意:wrap(byte[] array, int offset, int length)参数offset只是设置缓冲区的position值,length确定limit值

Demo:

byte[] byteArr = new byte[]{1,2,3,4,5,6,7,8};
ByteBuffer byteBuffer1 = ByteBuffer.wrap(byteArr);
ByteBuffer byteBuffer2 = ByteBuffer.wrap(byteArr,2,4);
System.out.println("bytebuffer1 capacity=" + byteBuffer1.capacity() + " limit=" + byteBuffer1.limit() + " position=" + byteBuffer1.position());
System.out.println("bytebuffer2 capacity=" + byteBuffer2.capacity() + " limit=" + byteBuffer2.limit() + " position=" + byteBuffer2.position());

output:
	bytebuffer1 capacity=8 limit=8 position=0
	bytebuffer2 capacity=8 limit=6 position=2

put(byte[] b)和get()方法的使用

get和put分别提供两种操作,相对位置和绝对位置操作。执行相对位置读或者写操作后,position递增

/**
     * Relative <i>get</i> method.  Reads the byte at this buffer's
     * current position, and then increments the position.
     *
     * @return  The byte at the buffer's current position
     *
     * @throws  BufferUnderflowException
     *          If the buffer's current position is not smaller than its limit
     */
    public abstract byte get();

    /**
     * Relative <i>put</i> method&nbsp;&nbsp;<i>(optional operation)</i>.
     *
     * <p> Writes the given byte into this buffer at the current
     * position, and then increments the position. </p>
     *
     * @param  b
     *         The byte to be written
     *
     * @return  This buffer
     *
     * @throws  BufferOverflowException
     *          If this buffer's current position is not smaller than its limit
     *
     * @throws  ReadOnlyBufferException
     *          If this buffer is read-only
     */
    public abstract ByteBuffer put(byte b);

    /**
     * Absolute <i>get</i> method.  Reads the byte at the given
     * index.
     *
     * @param  index
     *         The index from which the byte will be read
     *
     * @return  The byte at the given index
     *
     * @throws  IndexOutOfBoundsException
     *          If <tt>index</tt> is negative
     *          or not smaller than the buffer's limit
     */
    public abstract byte get(int index);

    /**
     * Absolute <i>put</i> method&nbsp;&nbsp;<i>(optional operation)</i>.
     *
     * <p> Writes the given byte into this buffer at the given
     * index. </p>
     *
     * @param  index
     *         The index at which the byte will be written
     *
     * @param  b
     *         The byte value to be written
     *
     * @return  This buffer
     *
     * @throws  IndexOutOfBoundsException
     *          If <tt>index</tt> is negative
     *          or not smaller than the buffer's limit
     *
     * @throws  ReadOnlyBufferException
     *          If this buffer is read-only
     */
    public abstract ByteBuffer put(int index, byte b);

put(byte[] src, int offset, int length)和get(byte[] dst, int offset, int length)

相对批量put方法,将给定源数组中的字节传输到此缓冲区当前位置中。

/**
     * Relative bulk <i>put</i> method&nbsp;&nbsp;<i>(optional operation)</i>.
     *
     * <p> This method transfers bytes into this buffer from the given
     * source array.  If there are more bytes to be copied from the array
     * than remain in this buffer, that is, if
     * <tt>length</tt>&nbsp;<tt>&gt;</tt>&nbsp;<tt>remaining()</tt>, then no
     * bytes are transferred and a {@link BufferOverflowException} is
     * thrown.
     *
     * <p> Otherwise, this method copies <tt>length</tt> bytes from the
     * given array into this buffer, starting at the given offset in the array
     * and at the current position of this buffer.  The position of this buffer
     * is then incremented by <tt>length</tt>.
     *
     * <p> In other words, an invocation of this method of the form
     * <tt>dst.put(src,&nbsp;off,&nbsp;len)</tt> has exactly the same effect as
     * the loop
     *
     * <pre>{@code
     *     for (int i = off; i < off + len; i++)
     *         dst.put(a[i]);
     * }</pre>
     *
     * except that it first checks that there is sufficient space in this
     * buffer and it is potentially much more efficient.
     *
     * @param  src
     *         The array from which bytes are to be read
     *
     * @param  offset
     *         The offset within the array of the first byte to be read;
     *         must be non-negative and no larger than <tt>array.length</tt>
     *
     * @param  length
     *         The number of bytes to be read from the given array;
     *         must be non-negative and no larger than
     *         <tt>array.length - offset</tt>
     *
     * @return  This buffer
     *
     * @throws  BufferOverflowException
     *          If there is insufficient space in this buffer
     *
     * @throws  IndexOutOfBoundsException
     *          If the preconditions on the <tt>offset</tt> and <tt>length</tt>
     *          parameters do not hold
     *
     * @throws  ReadOnlyBufferException
     *          If this buffer is read-only
     */
    public ByteBuffer put(byte[] src, int offset, int length) {
        checkBounds(offset, length, src.length);
        if (length > remaining())
            throw new BufferOverflowException();
        int end = offset + length;
        for (int i = offset; i < end; i++)
            this.put(src[i]);
        return this;
    }

dst.put(src,offset,length)等同于下面的循环语句

for(int i = offset;i < offset + length;i++){
	dst.put(a[i])
}

相对批量get方法,将缓冲区当前位置的字节传输到给定的目标数组中。

 // -- Bulk get operations --

    /**
     * Relative bulk <i>get</i> method.
     *
     * <p> This method transfers bytes from this buffer into the given
     * destination array.  If there are fewer bytes remaining in the
     * buffer than are required to satisfy the request, that is, if
     * <tt>length</tt>&nbsp;<tt>&gt;</tt>&nbsp;<tt>remaining()</tt>, then no
     * bytes are transferred and a {@link BufferUnderflowException} is
     * thrown.
     *
     * <p> Otherwise, this method copies <tt>length</tt> bytes from this
     * buffer into the given array, starting at the current position of this
     * buffer and at the given offset in the array.  The position of this
     * buffer is then incremented by <tt>length</tt>.
     *
     * <p> In other words, an invocation of this method of the form
     * <tt>src.get(dst,&nbsp;off,&nbsp;len)</tt> has exactly the same effect as
     * the loop
     *
     * <pre>{@code
     *     for (int i = off; i < off + len; i++)
     *         dst[i] = src.get():
     * }</pre>
     *
     * except that it first checks that there are sufficient bytes in
     * this buffer and it is potentially much more efficient.
     *
     * @param  dst
     *         The array into which bytes are to be written
     *
     * @param  offset
     *         The offset within the array of the first byte to be
     *         written; must be non-negative and no larger than
     *         <tt>dst.length</tt>
     *
     * @param  length
     *         The maximum number of bytes to be written to the given
     *         array; must be non-negative and no larger than
     *         <tt>dst.length - offset</tt>
     *
     * @return  This buffer
     *
     * @throws  BufferUnderflowException
     *          If there are fewer than <tt>length</tt> bytes
     *          remaining in this buffer
     *
     * @throws  IndexOutOfBoundsException
     *          If the preconditions on the <tt>offset</tt> and <tt>length</tt>
     *          parameters do not hold
     */
    public ByteBuffer get(byte[] dst, int offset, int length) {
        checkBounds(offset, length, dst.length);
        if (length > remaining())
            throw new BufferUnderflowException();
        int end = offset + length;
        for (int i = offset; i < end; i++)
            dst[i] = get();
        return this;
    }

Demo:

		byte[] byteArr1 = new byte[]{1,2,3,4,5,6,7,8};
        byte[] byteArr2 = new byte[]{55,66,77,88};
        ByteBuffer byteBuffer = ByteBuffer.allocate(10);
        byteBuffer.put(byteArr1);
        byteBuffer.position(2);
        byteBuffer.put(byteArr2,1,3);

        byte[] getByte = byteBuffer.array();
        for (int i = 0; i < getByte.length; i++) {
            System.out.print(getByte[i] + " ");
        }
        System.out.println();
        byteBuffer.position(1);
        byte[] byteArrOut = new byte[byteBuffer.capacity()];
        byteBuffer.get(byteArrOut,3,4);
        for (int i = 0; i < byteArrOut.length; i++) {
            System.out.print(byteArrOut[i] + " ");
        }
        System.out.println();

output:
	1 2 66 77 88 6 7 8 0 0 
	0 0 0 2 66 77 88 0 0 0 

put(ByteBuffer src)

相对批量put方法,将给定源缓冲区的剩余字节传输到此缓冲区的当前位置。

 // -- Bulk put operations --

    /**
     * Relative bulk <i>put</i> method&nbsp;&nbsp;<i>(optional operation)</i>.
     *
     * <p> This method transfers the bytes remaining in the given source
     * buffer into this buffer.  If there are more bytes remaining in the
     * source buffer than in this buffer, that is, if
     * <tt>src.remaining()</tt>&nbsp;<tt>&gt;</tt>&nbsp;<tt>remaining()</tt>,
     * then no bytes are transferred and a {@link
     * BufferOverflowException} is thrown.
     *
     * <p> Otherwise, this method copies
     * <i>n</i>&nbsp;=&nbsp;<tt>src.remaining()</tt> bytes from the given
     * buffer into this buffer, starting at each buffer's current position.
     * The positions of both buffers are then incremented by <i>n</i>.
     *
     * <p> In other words, an invocation of this method of the form
     * <tt>dst.put(src)</tt> has exactly the same effect as the loop
     *
     * <pre>
     *     while (src.hasRemaining())
     *         dst.put(src.get()); </pre>
     *
     * except that it first checks that there is sufficient space in this
     * buffer and it is potentially much more efficient.
     *
     * @param  src
     *         The source buffer from which bytes are to be read;
     *         must not be this buffer
     *
     * @return  This buffer
     *
     * @throws  BufferOverflowException
     *          If there is insufficient space in this buffer
     *          for the remaining bytes in the source buffer
     *
     * @throws  IllegalArgumentException
     *          If the source buffer is this buffer
     *
     * @throws  ReadOnlyBufferException
     *          If this buffer is read-only
     */
    public ByteBuffer put(ByteBuffer src) {
        if (src == this)
            throw new IllegalArgumentException();
        if (isReadOnly())
            throw new ReadOnlyBufferException();
        int n = src.remaining();
        if (n > remaining())
            throw new BufferOverflowException();
        for (int i = 0; i < n; i++)
            put(src.get());
        return this;
    }

Demo

		byte[] byteArr1 = new byte[]{1,2,3,4,5,6,7,8};
        ByteBuffer buffer1 = ByteBuffer.wrap(byteArr1);

        byte[] byteArr2 = new byte[]{55,66,77,88};
        ByteBuffer buffer2 = ByteBuffer.wrap(byteArr2);

        buffer1.position(4);
        buffer2.position(1);

        buffer1.put(buffer2);

        System.out.println(buffer1.position());
        System.out.println(buffer2.position());

        byte[] byteArrOut = buffer1.array();
        for (int i = 0; i < byteArrOut.length; i++) {
            System.out.print(byteArrOut[i] + " ");
        }
        System.out.println();
    
  output:
  		7
		4
		1 2 3 4 66 77 88 8 

putType()和getType()

putChar(char value)

 /**
     * Relative <i>put</i> method for writing a char
     * value&nbsp;&nbsp;<i>(optional operation)</i>.
     *
     * <p> Writes two bytes containing the given char value, in the
     * current byte order, into this buffer at the current position, and then
     * increments the position by two.  </p>
     *
     * @param  value
     *         The char value to be written
     *
     * @return  This buffer
     *
     * @throws  BufferOverflowException
     *          If there are fewer than two bytes
     *          remaining in this buffer
     *
     * @throws  ReadOnlyBufferException
     *          If this buffer is read-only
     */
    public abstract ByteBuffer putChar(char value);

putChar(int index, char value) putDouble(double value) //8个字节 putDouble(int index, double value) putFloat(float value) //4个字节 putFloat(int index, float value) putInt(int value) //4个字节 putInt(int index, int value) putLong(long value) //8个字节 putLong(int index, int value) putShort(short value) //2个字节 putShort(int index, short value)

slice()方法

创建新的字节缓冲区,其内容是此缓冲区内容的共享子序列。新缓冲区的内容将从此缓冲区的当前位置开始。此缓冲区内容的更改子新缓冲区是可见的,反之亦然;两个缓冲区的位置、限制和标记值是相互独立的。新缓冲区的位置将为0,其容量和限制将为此缓冲区中所剩余的字节数量,标记是不确定的

 /**
     * Creates a new byte buffer whose content is a shared subsequence of
     * this buffer's content.
     *
     * <p> The content of the new buffer will start at this buffer's current
     * position.  Changes to this buffer's content will be visible in the new
     * buffer, and vice versa; the two buffers' position, limit, and mark
     * values will be independent.
     *
     * <p> The new buffer's position will be zero, its capacity and its limit
     * will be the number of bytes remaining in this buffer, and its mark
     * will be undefined.  The new buffer will be direct if, and only if, this
     * buffer is direct, and it will be read-only if, and only if, this buffer
     * is read-only.  </p>
     *
     * @return  The new byte buffer
     */
    public abstract ByteBuffer slice();

Demo

 		byte[] byteArr1 = new byte[]{1,2,3,4,5,6,7,8};
        ByteBuffer buffer1 = ByteBuffer.wrap(byteArr1);

        buffer1.position(4);
        ByteBuffer buffer2 = buffer1.slice();
        System.out.println("buffer1 position=" + buffer1.position() + " capacity=" + buffer1.capacity() + " limit=" + buffer1.limit());
        System.out.println("buffer2 position=" + buffer2.position() + " capacity=" + buffer2.capacity() + " limit=" + buffer2.limit());

        buffer2.put(0,(byte)100);
        byte[] byteArrOut1 = buffer1.array();
        for (int i = 0; i < byteArrOut1.length; i++) {
            System.out.print(byteArrOut1[i] + " ");
        }
        System.out.println();
        byte[] byteArrOut2 = buffer1.array();
        for (int i = 0; i < byteArrOut2.length; i++) {
            System.out.print(byteArrOut2[i] + " ");
        }
        System.out.println();

output:
	buffer1 position=4 capacity=8 limit=8
	buffer2 position=0 capacity=4 limit=4
	1 2 3 4 100 6 7 8 
	1 2 3 4 100 6 7 8 

转换为CharBuffer字符缓冲区及中文的处理

asCharBuffer

/**
     * Creates a view of this byte buffer as a char buffer.
     *
     * <p> The content of the new buffer will start at this buffer's current
     * position.  Changes to this buffer's content will be visible in the new
     * buffer, and vice versa; the two buffers' position, limit, and mark
     * values will be independent.
     *
     * <p> The new buffer's position will be zero, its capacity and its limit
     * will be the number of bytes remaining in this buffer divided by
     * two, and its mark will be undefined.  The new buffer will be direct
     * if, and only if, this buffer is direct, and it will be read-only if, and
     * only if, this buffer is read-only.  </p>
     *
     * @return  A new char buffer
     */
    public abstract CharBuffer asCharBuffer();

Demo

		byte[] byteArr1 = "我是好学生".getBytes();
        System.out.println(Charset.defaultCharset().name());

        ByteBuffer byteBuffer = ByteBuffer.wrap(byteArr1);
        System.out.println(byteBuffer.getClass().getName());

        CharBuffer charBuffer = byteBuffer.asCharBuffer();
        System.out.println(charBuffer.getClass().getName());

        System.out.println("byteBuffer position=" + byteBuffer.position() + " capacity=" + byteBuffer.capacity() + " limit=" + byteBuffer.limit());
        System.out.println("charBuffer position=" + charBuffer.position() + " capacity=" + charBuffer.capacity() + " limit=" + charBuffer.limit());

        charBuffer.position(0);
        for (int i = 0; i < charBuffer.capacity(); i++) {
            System.out.print(charBuffer.get() + " ");
        }
        System.out.println();
        
output:
	UTF-8
	java.nio.HeapByteBuffer
	java.nio.ByteBufferAsCharBufferB	
	byteBuffer position=0 capacity=15 limit=15
	charBuffer position=0 capacity=7 limit=7
	 釦 颯  뷥 궦  

出现了乱码。 byteArr1数组中存储的编码为UTF-8,wrap后,缓冲区存储的编码也为UTF-8,asCharBuffer后,UTF-8编码的ByteBuffer转换成UTF-8的CharBuffer,在调用charBuffer的get方法时,以UTF-16BE的编码格式获得中文时出现编码不匹配的情况,出现了乱码

解决方法1: 将中文按utf-16be编码转化成字节数组

byte[] byteArr1 = "我是好学生".getBytes("utf-16BE");

解决方法2:

byte[] byteArr1 = "我是好学生".getBytes("utf-8");
……
CharBuffer charBuffer = Charset.forName("utf-8").decode(byteBuffer)
……

设置与获得字节顺序

order()方法与字节数据排列的顺序有关,不同的CPU在读取字节时的顺序是不一样的,有的CPU从高位开始读,有的CPU从低位开始读,order(ByteOrder bo)设置字节的排列顺序。 ByteOrder order()方法的作用:获取此缓冲区的字节顺序。新创建的字节缓冲区的顺序始终为BIG_ENDIAN。 1):public static final ByteOrder BIG_ENDIAN:表示BIG_ENDIAN字节顺序的常量。按照此顺序,多字节值的字节顺序是从最高有效位到最低有效位的。 2):public static final ByteOrder LITTLE_ENDIAN:表示LITTLE_ENDIAN字节顺序的常量。按照此顺序,多字节值的字节顺序是从最低有效位到最高有效位的。 order(ByteOrder bo):修改此缓冲区的字节顺序,默认情况下,字节缓冲区的初始顺序是BIG_ENDIAN。

创建只读缓冲区

asReadOnlyBuffer():创建共享此缓冲区内容的新的只读字节缓冲区。新缓冲区的内容将为此缓冲区的内容。此缓冲区内容的更改在新缓冲区可见,新缓冲区内容是只读的

		byte[] byteArrIn = {1,2,3,4,5};
        ByteBuffer buffer1 = ByteBuffer.wrap(byteArrIn);
        ByteBuffer buffer2 = buffer1.asReadOnlyBuffer();
        System.out.println(buffer1.isReadOnly());
        System.out.println(buffer2.isReadOnly());
        buffer2.rewind();
        buffer2.put((byte)111);

output:
	false
	true
	java.nio.ReadOnlyBufferException
		at java.nio.HeapByteBufferR.put(HeapByteBufferR.java:172)

压缩缓冲区

compact:将缓冲区的当前位置和限制之间的字节复制到缓冲区的开始处,即将索引p=position()处的字节复制到索引0处,将索引p+1处的字节复制到索引1处,依此类推,直到将索引limit()-1处的自己复制到索引n = limit() – 1 -p处。然后,将缓冲区的的位置设置为n+1,并将其限制设置为其容量。

/**
     * Compacts this buffer&nbsp;&nbsp;<i>(optional operation)</i>.
     *
     * <p> The bytes between the buffer's current position and its limit,
     * if any, are copied to the beginning of the buffer.  That is, the
     * byte at index <i>p</i>&nbsp;=&nbsp;<tt>position()</tt> is copied
     * to index zero, the byte at index <i>p</i>&nbsp;+&nbsp;1 is copied
     * to index one, and so forth until the byte at index
     * <tt>limit()</tt>&nbsp;-&nbsp;1 is copied to index
     * <i>n</i>&nbsp;=&nbsp;<tt>limit()</tt>&nbsp;-&nbsp;<tt>1</tt>&nbsp;-&nbsp;<i>p</i>.
     * The buffer's position is then set to <i>n+1</i> and its limit is set to
     * its capacity.  The mark, if defined, is discarded.
     *
     * <p> The buffer's position is set to the number of bytes copied,
     * rather than to zero, so that an invocation of this method can be
     * followed immediately by an invocation of another relative <i>put</i>
     * method. </p>
     *

     *
     * <p> Invoke this method after writing data from a buffer in case the
     * write was incomplete.  The following loop, for example, copies bytes
     * from one channel to another via the buffer <tt>buf</tt>:
     *
     * <blockquote><pre>{@code
     *   buf.clear();          // Prepare buffer for use
     *   while (in.read(buf) >= 0 || buf.position != 0) {
     *       buf.flip();
     *       out.write(buf);
     *       buf.compact();    // In case of partial write
     *   }
     * }</pre></blockquote>
     *

     *
     * @return  This buffer
     *
     * @throws  ReadOnlyBufferException
     *          If this buffer is read-only
     */
    public abstract ByteBuffer compact();

比较缓冲区内容

方法一: equals:

/**
     * Tells whether or not this buffer is equal to another object.
     * <p> Two byte buffers are equal if, and only if,
     * <ol>
     *   <li><p> They have the same element type,  </p></li>
     *   <li><p> They have the same number of remaining elements, and
     *   </p></li>
     *   <li><p> The two sequences of remaining elements, considered
     *   independently of their starting positions, are pointwise equal.
     * <p> A byte buffer is not equal to any other type of object.  </p>
    
     * @param  ob  The object to which this buffer is to be compared
     *
     * @return  <tt>true</tt> if, and only if, this buffer is equal to the
     *           given object
     */
    public boolean equals(Object ob) {
        if (this == ob)
            return true;
        if (!(ob instanceof ByteBuffer))
            return false;
        ByteBuffer that = (ByteBuffer)ob;
        if (this.remaining() != that.remaining())
            return false;
        int p = this.position();
        for (int i = this.limit() - 1, j = that.limit() - 1; i >= p; i--, j--)
            if (!equals(this.get(i), that.get(j)))
                return false;
        return true;
    }
  1. 判断是否是自身,如果是自身,返回true
  2. 判断是不是ByteBuffer类的实例,如果不是,返回false;
  3. 判断remaining是否一样,不一样,返回false;
  4. 判断position和limit是否一样,有一个不一样,返回false。

从源码看,两个缓冲区的capacity可以不一样。

方法二: compareTo

 /**
     * Compares this buffer to another.
     *
     * <p> Two byte buffers are compared by comparing their sequences of
     * remaining elements lexicographically, without regard to the starting
     * position of each sequence within its corresponding buffer.
     * Pairs of {@code byte} elements are compared as if by invoking
     * {@link Byte#compare(byte,byte)}.
     * <p> A byte buffer is not comparable to any other type of object.
     *
     * @return  A negative integer, zero, or a positive integer as this buffer
     *          is less than, equal to, or greater than the given buffer
     */
    public int compareTo(ByteBuffer that) {
        int n = this.position() + Math.min(this.remaining(), that.remaining());
        for (int i = this.position(), j = that.position(); i < n; i++, j++) {
            int cmp = compare(this.get(i), that.get(j));
            if (cmp != 0)
                return cmp;
        }
        return this.remaining() - that.remaining();
    }

1)判断两个ByteBuffer的范围是从当前ByteBuffer对象的当前位置开始,以两个ByteBuffer对象最小的remaining结束,说明判断的范围是remaining交集 2) 如果在开始和结束的范围之间有一个字节不同,则返回两者的减数 3) 如果在开始和结束的范围之间每个字节都相同,则返回两者remaining的减数

复制缓冲区

 /**
     * Creates a new byte buffer that shares this buffer's content.
     *
     * <p> The content of the new buffer will be that of this buffer.  Changes
     * to this buffer's content will be visible in the new buffer, and vice
     * versa; the two buffers' position, limit, and mark values will be
     * independent.
     *
     * <p> The new buffer's capacity, limit, position, and mark values will be
     * identical to those of this buffer.  The new buffer will be direct if,
     * and only if, this buffer is direct, and it will be read-only if, and
     * only if, this buffer is read-only.  </p>
     *
     * @return  The new byte buffer
     */
    public abstract ByteBuffer duplicate();

对缓冲区扩容

 public static ByteBuffer extendsSize(ByteBuffer byteBuffer,int extendSize){
        ByteBuffer newByteBuffer = ByteBuffer.allocate(byteBuffer.capacity() + extendSize);
        newByteBuffer.put(byteBuffer);
        return newByteBuffer;
    }

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员栈长,转载请注明出处:https://javaforall.cn/186718.html原文链接:https://javaforall.cn

原文地址:https://cloud.tencent.com/developer/article/2157274

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


学习编程是顺着互联网的发展潮流,是一件好事。新手如何学习编程?其实不难,不过在学习编程之前你得先了解你的目的是什么?这个很重要,因为目的决定你的发展方向、决定你的发展速度。
IT行业是什么工作做什么?IT行业的工作有:产品策划类、页面设计类、前端与移动、开发与测试、营销推广类、数据运营类、运营维护类、游戏相关类等,根据不同的分类下面有细分了不同的岗位。
女生学Java好就业吗?女生适合学Java编程吗?目前有不少女生学习Java开发,但要结合自身的情况,先了解自己适不适合去学习Java,不要盲目的选择不适合自己的Java培训班进行学习。只要肯下功夫钻研,多看、多想、多练
Can’t connect to local MySQL server through socket \'/var/lib/mysql/mysql.sock问题 1.进入mysql路径
oracle基本命令 一、登录操作 1.管理员登录 # 管理员登录 sqlplus / as sysdba 2.普通用户登录
一、背景 因为项目中需要通北京网络,所以需要连vpn,但是服务器有时候会断掉,所以写个shell脚本每五分钟去判断是否连接,于是就有下面的shell脚本。
BETWEEN 操作符选取介于两个值之间的数据范围内的值。这些值可以是数值、文本或者日期。
假如你已经使用过苹果开发者中心上架app,你肯定知道在苹果开发者中心的web界面,无法直接提交ipa文件,而是需要使用第三方工具,将ipa文件上传到构建版本,开...
下面的 SQL 语句指定了两个别名,一个是 name 列的别名,一个是 country 列的别名。**提示:**如果列名称包含空格,要求使用双引号或方括号:
在使用H5混合开发的app打包后,需要将ipa文件上传到appstore进行发布,就需要去苹果开发者中心进行发布。​
+----+--------------+---------------------------+-------+---------+
数组的声明并不是声明一个个单独的变量,比如 number0、number1、...、number99,而是声明一个数组变量,比如 numbers,然后使用 nu...
第一步:到appuploader官网下载辅助工具和iCloud驱动,使用前面创建的AppID登录。
如需删除表中的列,请使用下面的语法(请注意,某些数据库系统不允许这种在数据库表中删除列的方式):
前不久在制作win11pe,制作了一版,1.26GB,太大了,不满意,想再裁剪下,发现这次dism mount正常,commit或discard巨慢,以前都很快...
赛门铁克各个版本概览:https://knowledge.broadcom.com/external/article?legacyId=tech163829
实测Python 3.6.6用pip 21.3.1,再高就报错了,Python 3.10.7用pip 22.3.1是可以的
Broadcom Corporation (博通公司,股票代号AVGO)是全球领先的有线和无线通信半导体公司。其产品实现向家庭、 办公室和移动环境以及在这些环境...
发现个问题,server2016上安装了c4d这些版本,低版本的正常显示窗格,但红色圈出的高版本c4d打开后不显示窗格,
TAT:https://cloud.tencent.com/document/product/1340