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

org.testifyproject.guava.common.io.CharStreams Maven / Gradle / Ivy

There is a newer version: 1.0.6
Show newest version
/*
 * Copyright (C) 2007 The Guava Authors
 *
 * Licensed 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.testifyproject.guava.common.io;

import static org.testifyproject.guava.common.base.Preconditions.checkNotNull;
import static org.testifyproject.guava.common.base.Preconditions.checkPositionIndexes;

import org.testifyproject.guava.common.annotations.Beta;
import org.testifyproject.guava.common.annotations.GwtIncompatible;
import org.testifyproject.guava.errorprone.annotations.CanIgnoreReturnValue;
import java.io.Closeable;
import java.io.EOFException;
import java.io.IOException;
import java.io.Reader;
import java.io.Writer;
import java.nio.CharBuffer;
import java.util.ArrayList;
import java.util.List;

/**
 * Provides utility methods for working with character streams.
 *
 * 

All method parameters must be non-null unless documented otherwise. * *

Some of the methods in this class take arguments with a generic type of * {@code Readable & Closeable}. A {@link java.io.Reader} implements both of those interfaces. * Similarly for {@code Appendable & Closeable} and {@link java.io.Writer}. * * @author Chris Nokleberg * @author Bin Zhu * @author Colin Decker * @since 1.0 */ @Beta @GwtIncompatible public final class CharStreams { // 2K chars (4K bytes) private static final int DEFAULT_BUF_SIZE = 0x800; /** * Creates a new {@code CharBuffer} for buffering reads or writes. */ static CharBuffer createBuffer() { return CharBuffer.allocate(DEFAULT_BUF_SIZE); } private CharStreams() {} /** * Copies all characters between the {@link Readable} and {@link Appendable} objects. Does not * close or flush either object. * * @param from the object to read from * @param to the object to write to * @return the number of characters copied * @throws IOException if an I/O error occurs */ @CanIgnoreReturnValue public static long copy(Readable from, Appendable to) throws IOException { // The most common case is that from is a Reader (like InputStreamReader or StringReader) so // take advantage of that. if (from instanceof Reader) { // optimize for common output types which are optimized to deal with char[] if (to instanceof StringBuilder) { return copyReaderToBuilder((Reader) from, (StringBuilder) to); } else { return copyReaderToWriter((Reader) from, asWriter(to)); } } else { checkNotNull(from); checkNotNull(to); long total = 0; CharBuffer buf = createBuffer(); while (from.read(buf) != -1) { buf.flip(); to.append(buf); total += buf.remaining(); buf.clear(); } return total; } } // TODO(lukes): consider allowing callers to pass in a buffer to use, some callers would be able // to reuse buffers, others would be able to size them more appropriately than the constant // defaults /** * Copies all characters between the {@link Reader} and {@link StringBuilder} objects. Does not * close or flush the reader. * *

This is identical to {@link #copy(Readable, Appendable)} but optimized for these specific * types. CharBuffer has poor performance when being written into or read out of so round tripping * all the bytes through the buffer takes a long time. With these specialized types we can just * use a char array. * * @param from the object to read from * @param to the object to write to * @return the number of characters copied * @throws IOException if an I/O error occurs */ @CanIgnoreReturnValue static long copyReaderToBuilder(Reader from, StringBuilder to) throws IOException { checkNotNull(from); checkNotNull(to); char[] buf = new char[DEFAULT_BUF_SIZE]; int nRead; long total = 0; while ((nRead = from.read(buf)) != -1) { to.append(buf, 0, nRead); total += nRead; } return total; } /** * Copies all characters between the {@link Reader} and {@link Writer} objects. Does not close or * flush the reader or writer. * *

This is identical to {@link #copy(Readable, Appendable)} but optimized for these specific * types. CharBuffer has poor performance when being written into or read out of so round tripping * all the bytes through the buffer takes a long time. With these specialized types we can just * use a char array. * * @param from the object to read from * @param to the object to write to * @return the number of characters copied * @throws IOException if an I/O error occurs */ @CanIgnoreReturnValue static long copyReaderToWriter(Reader from, Writer to) throws IOException { checkNotNull(from); checkNotNull(to); char[] buf = new char[DEFAULT_BUF_SIZE]; int nRead; long total = 0; while ((nRead = from.read(buf)) != -1) { to.write(buf, 0, nRead); total += nRead; } return total; } /** * Reads all characters from a {@link Readable} object into a {@link String}. Does not close the * {@code Readable}. * * @param r the object to read from * @return a string containing all the characters * @throws IOException if an I/O error occurs */ public static String toString(Readable r) throws IOException { return toStringBuilder(r).toString(); } /** * Reads all characters from a {@link Readable} object into a new {@link StringBuilder} instance. * Does not close the {@code Readable}. * * @param r the object to read from * @return a {@link StringBuilder} containing all the characters * @throws IOException if an I/O error occurs */ private static StringBuilder toStringBuilder(Readable r) throws IOException { StringBuilder sb = new StringBuilder(); if (r instanceof Reader) { copyReaderToBuilder((Reader) r, sb); } else { copy(r, sb); } return sb; } /** * Reads all of the lines from a {@link Readable} object. The lines do not include * line-termination characters, but do include other leading and trailing whitespace. * *

Does not close the {@code Readable}. If reading files or resources you should use the * {@link Files#readLines} and {@link Resources#readLines} methods. * * @param r the object to read from * @return a mutable {@link List} containing all the lines * @throws IOException if an I/O error occurs */ public static List readLines(Readable r) throws IOException { List result = new ArrayList<>(); LineReader lineReader = new LineReader(r); String line; while ((line = lineReader.readLine()) != null) { result.add(line); } return result; } /** * Streams lines from a {@link Readable} object, stopping when the processor returns {@code false} * or all lines have been read and returning the result produced by the processor. Does not close * {@code readable}. Note that this method may not fully consume the contents of {@code readable} * if the processor stops processing early. * * @throws IOException if an I/O error occurs * @since 14.0 */ @CanIgnoreReturnValue // some processors won't return a useful result public static T readLines(Readable readable, LineProcessor processor) throws IOException { checkNotNull(readable); checkNotNull(processor); LineReader lineReader = new LineReader(readable); String line; while ((line = lineReader.readLine()) != null) { if (!processor.processLine(line)) { break; } } return processor.getResult(); } /** * Reads and discards data from the given {@code Readable} until the end of the stream is * reached. Returns the total number of chars read. Does not close the stream. * * @since 20.0 */ @CanIgnoreReturnValue public static long exhaust(Readable readable) throws IOException { long total = 0; long read; CharBuffer buf = createBuffer(); while ((read = readable.read(buf)) != -1) { total += read; buf.clear(); } return total; } /** * Discards {@code n} characters of data from the reader. This method will block until the full * amount has been skipped. Does not close the reader. * * @param reader the reader to read from * @param n the number of characters to skip * @throws EOFException if this stream reaches the end before skipping all the characters * @throws IOException if an I/O error occurs */ public static void skipFully(Reader reader, long n) throws IOException { checkNotNull(reader); while (n > 0) { long amt = reader.skip(n); if (amt == 0) { throw new EOFException(); } n -= amt; } } /** * Returns a {@link Writer} that simply discards written chars. * * @since 15.0 */ public static Writer nullWriter() { return NullWriter.INSTANCE; } private static final class NullWriter extends Writer { private static final NullWriter INSTANCE = new NullWriter(); @Override public void write(int c) {} @Override public void write(char[] cbuf) { checkNotNull(cbuf); } @Override public void write(char[] cbuf, int off, int len) { checkPositionIndexes(off, off + len, cbuf.length); } @Override public void write(String str) { checkNotNull(str); } @Override public void write(String str, int off, int len) { checkPositionIndexes(off, off + len, str.length()); } @Override public Writer append(CharSequence csq) { checkNotNull(csq); return this; } @Override public Writer append(CharSequence csq, int start, int end) { checkPositionIndexes(start, end, csq.length()); return this; } @Override public Writer append(char c) { return this; } @Override public void flush() {} @Override public void close() {} @Override public String toString() { return "CharStreams.nullWriter()"; } } /** * Returns a Writer that sends all output to the given {@link Appendable} target. Closing the * writer will close the target if it is {@link Closeable}, and flushing the writer will flush the * target if it is {@link java.io.Flushable}. * * @param target the object to which output will be sent * @return a new Writer object, unless target is a Writer, in which case the target is returned */ public static Writer asWriter(Appendable target) { if (target instanceof Writer) { return (Writer) target; } return new AppendableWriter(target); } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy