All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.apache.oodt.commons.io.FixedBufferOutputStream Maven / Gradle / Ivy

There is a newer version: 1.9.1
Show newest version
// Licensed to the Apache Software Foundation (ASF) under one or more contributor
// license agreements.  See the NOTICE.txt file distributed with this work for
// additional information regarding copyright ownership.  The ASF licenses this
// file to you under the Apache License, Version 2.0 (the "License"); you may not
// use this file except in compliance with the License.  You may obtain a copy of
// the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
// License for the specific language governing permissions and limitations under
// the License.

package org.apache.oodt.commons.io;

import java.io.IOException;
import java.io.OutputStream;

/** This stream writes its output into a byte buffer of fixed length.
 *
 * For a buffer of size n, only the last n bytes written are ever
 * available.
 *
 * @author Kelly
 */
public class FixedBufferOutputStream extends OutputStream {
	/** Construct a fixed buffer output stream.
	 *
	 * @param n Size of the buffer.
	 */
	public FixedBufferOutputStream(int n) {
		if (n < 0) {
		  throw new IllegalArgumentException("Buffer size must be nonnegative");
		}
		buffer = new byte[n];
		length = n;
		size = 0;
		start = 0;
	}

	public void write(int b) throws IOException {
		checkIfClosed();
		if (length == 0) {
		  return;
		}
		if (size < length) {
		  buffer[size++] = (byte) b;
		} else {
			buffer[start] = (byte) b;
			start = (start + 1) % length;
		}
	}

	public void write(byte[] a, int off, int len) throws IOException {
		checkIfClosed();
		if (a == null) {
		  throw new NullPointerException("Can't write from a null array");
		} else if ((off < 0) || (off > a.length) || (len < 0) || ((off + len) > a.length) || ((off + len) < 0)) {
			throw new IndexOutOfBoundsException("Offset " + off + " and length " + len + " not within array bounds");
		} else if (len == 0) {
			return;
		}
		if (len > length) {
			off += len - length;
			len = length;
		}
		int capacity = length - size;
		int insertionIndex = size < length? size : start;
		int insertionLength = Math.min(length - insertionIndex, len);
		int remaining = len - insertionLength;
		System.arraycopy(a, off, buffer, insertionIndex, insertionLength);
		if (remaining > 0) {
			System.arraycopy(a, off + insertionLength, buffer, 0, remaining);
			start = remaining;
		} else if (capacity == 0) {
		  start = insertionIndex + insertionLength;
		}
		size = Math.min(length, size + len);
	}

	public void flush() {
		// Nothing need be done here
	}

	public void close() {
		start = -1;
	}

	/** Get the buffer.
	 *
	 * This method constructs a new array whose contents is the data written.  Its
	 * size is equal to the smaller of the number of bytes written or the size of the
	 * fixed buffer passed to the constructor of this class.
	 *
	 * @return The buffer.
	 */
	public byte[] getBuffer() {
		byte[] rc = new byte[Math.min(size, length)];
		System.arraycopy(buffer, start, rc, 0, size - start);
		System.arraycopy(buffer, 0, rc, size - start, start);
		return rc;
	}

	/** Throw an exception if we've been closed.
	 *
	 * @throws IOException If this stream has been closed.
	 */
	private void checkIfClosed() throws IOException {
		if (start == -1) {
		  throw new IOException("Can't write to closed stream");
		}
	}

	/** Length of the buffer. */
	private int length;

	/** Current size of the data in the buffer. */
	private int size;

	/** Current start offset of the data in the buffer.  If negative, buffer is closed. */
	private int start;

	/** The buffer. */
	private byte[] buffer;
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy