Reader 与 Guava MultiReader
Reader是Java IO体系里字符处理读取流的基本类,代码如下
/*
* %W% %E%
*
* Copyright (c) 2006, Oracle and/or its affiliates. All rights reserved.
* ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
*/ package java.io; /**
* Abstract class for reading character streams. The only methods that a
* subclass must implement are read(char[], int, int) and close(). Most
* subclasses, however, will override some of the methods defined here in order
* to provide higher efficiency, additional functionality, or both.
*
*
* @see BufferedReader
* @see LineNumberReader
* @see CharArrayReader
* @see InputStreamReader
* @see FileReader
* @see FilterReader
* @see PushbackReader
* @see PipedReader
* @see StringReader
* @see Writer
*
* @version %I%, %E%
* @author Mark Reinhold
* @since JDK1.1
*/ public abstract class Reader implements Readable, Closeable { /**
* 锁,在构造方法时赋值,默认使用this,也可以指定别的obj
*/
protected Object lock; /**
* Creates a new character-stream reader whose critical sections will
* synchronize on the reader itself.
*/
protected Reader() {
this.lock = this;
} /**
* Creates a new character-stream reader whose critical sections will
* synchronize on the given object.
*
* @param lock The Object to synchronize on.
*/
protected Reader(Object lock) {
if (lock == null) {
throw new NullPointerException();
}
this.lock = lock;
} /**
* Attempts to read characters into the specified character buffer.
* The buffer is used as a repository of characters as-is: the only
* changes made are the results of a put operation. No flipping or
* rewinding of the buffer is performed.
*
* @param target the buffer to read characters into
* @return The number of characters added to the buffer, or
* -1 if this source of characters is at its end
* @throws IOException if an I/O error occurs
* @throws NullPointerException if target is null
* @throws ReadOnlyBufferException if target is a read only buffer
* @since 1.5
*/
public int read(java.nio.CharBuffer target) throws IOException {
int len = target.remaining();
char[] cbuf = new char[len];
int n = read(cbuf, 0, len);
if (n > 0)
target.put(cbuf, 0, n);
return n;
} /**
* 读取一个字符,实现方式是先读取一个字符到一个char数组中,最后返回数组的第一个元素
*/
public int read() throws IOException {
char cb[] = new char[1];
if (read(cb, 0, 1) == -1)
return -1;
else
return cb[0];
} /**
* 读取char[]数组长度的字符到数组中
*/
public int read(char cbuf[]) throws IOException {
return read(cbuf, 0, cbuf.length);
} /**
* 交给子类实现的读取方法
*/
abstract public int read(char cbuf[], int off, int len) throws IOException; /** Maximum skip-buffer size */
private static final int maxSkipBufferSize = 8192; /** 用来支持skip方法的数组 */
private char skipBuffer[] = null; /**
* 跳过指定数目的字符,实现方式是将指定字符读取出来并丢弃
* 另外,这个方法是个串行方法
*/
public long skip(long n) throws IOException {
if (n < 0L)
throw new IllegalArgumentException("skip value is negative");
int nn = (int) Math.min(n, maxSkipBufferSize);
synchronized (lock) {
if ((skipBuffer == null) || (skipBuffer.length < nn))
skipBuffer = new char[nn];
long r = n;
while (r > 0) {
int nc = read(skipBuffer, 0, (int)Math.min(r, nn));
if (nc == -1)
break;
r -= nc;
}
return n - r;
}
} /**
* 用来表示Reader中后面还有没有可读取的字符
* 在本类中始终返回false,在子类中有自己的实现
*/
public boolean ready() throws IOException {
return false;
} /**
* Tells whether this stream supports the mark() operation. The default
* implementation always returns false. Subclasses should override this
* method.
*
* @return true if and only if this stream supports the mark operation.
*/
public boolean markSupported() {
return false;
} /**
* 在指定位置做一个标记,用处类似于ByteBuffer中的mark
*/
public void mark(int readAheadLimit) throws IOException {
throw new IOException("mark() not supported");
} /**
* 将position设置为mark
*/
public void reset() throws IOException {
throw new IOException("reset() not supported");
} /**
* Closes the stream and releases any system resources associated with
* it. Once the stream has been closed, further read(), ready(),
* mark(), reset(), or skip() invocations will throw an IOException.
* Closing a previously closed stream has no effect.
*
* @exception IOException If an I/O error occurs
*/
abstract public void close() throws IOException; }
MultiReader
/*
* Copyright (C) 2008 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 com.google.common.io; import com.google.common.base.Preconditions; import java.io.IOException;
import java.io.Reader;
import java.util.Iterator; /**
* 使用多个Reader合成一个MultiReader,其中Reader被Supplier包装起来
*/
class MultiReader extends Reader {
private final Iterator<? extends InputSupplier<? extends Reader>> it;
/** 当前Reader */
private Reader current; MultiReader(Iterator<? extends InputSupplier<? extends Reader>> readers)
throws IOException {
this.it = readers;
advance();
} /**
* 关闭当前Reader并跳到下一个reader
*/
private void advance() throws IOException {
close();
if (it.hasNext()) {
current = it.next().getInput();
}
} /**
* 读取当前Reader的内容到cbuf[]中,如果当前reader已经读完,则切换到下一个reader来读取
*/
@Override public int read(char cbuf[], int off, int len) throws IOException {
if (current == null) {
return -1;
}
int result = current.read(cbuf, off, len);
if (result == -1) {
advance();
return read(cbuf, off, len);
}
return result;
} /**
* 跳过指定个数目的字符,如果当前reader已经读完,则跳到下一个reader并重新读取
*/
@Override public long skip(long n) throws IOException {
Preconditions.checkArgument(n >= 0, "n is negative");
if (n > 0) {
while (current != null) {
long result = current.skip(n);
if (result > 0) {
return result;
}
advance();
}
}
return 0;
} @Override public boolean ready() throws IOException {
return (current != null) && current.ready();
} /**
* 关闭当前reader
*/
@Override public void close() throws IOException {
if (current != null) {
try {
current.close();
} finally {
current = null;
}
}
}
}
Reader 与 Guava MultiReader的更多相关文章
- lucene.net的一个动态更新类
工作的需要,需要对于lucene.net索引即时的更新,毕竟lucene.net的索引重建的话比较慢,数据量大的时候建下要几天,所以就写个了缓冲类来解决即时的更新的问题,其实还是比较简单的. 大体上的 ...
- go标准库的学习-io
参考https://studygolang.com/pkgdoc 导入方式: import "io" o包提供了对I/O原语的基本接口.本包的基本任务是包装这些原语已有的实现(如o ...
- Lucene 4.0 正式版发布,亮点特性中文解读[转]
http://blog.csdn.net/accesine960/article/details/8066877 2012年10月12日,Lucene 4.0正式发布了(点击这里下载最新版),这个版本 ...
- ZXing 二维码解析生成工具类
原文:http://www.open-open.com/code/view/1455848023292 import com.google.zxing.*; import com.google.zxi ...
- 使用 Google Guava 美化你的 Java 代码
文章转载自:http://my.oschina.net/leejun2005/blog/172328 目录:[ - ] 1-使用 GOOGLE COLLECTIONS,GUAVA,STATIC IMP ...
- guava学习--File1
ByteSource:表示一个可读的字节.通常情况下,我们期望的字节来源是一个文件,但它也可以从一个字节数组读取字节. File f1 = new File("D:\\test2.txt&q ...
- Guava 9-I/O
字节流和字符流 Guava使用术语”流” 来表示可关闭的,并且在底层资源中有位置状态的I/O数据流.术语”字节流”指的是InputStream或OutputStream,”字符流”指的是Reader ...
- Guava 教程1-使用 Google Collections,Guava,static imports 编写漂亮代码
原文出处: oschina (API:http://ifeve.com/category/framework/guava-2/ JAR DOC Source 链接:http://pan.baidu.c ...
- Guava Files 源码分析(一)
Files中的工厂 Files类中对InputStream, OutputStream以及Reader,Writer的操作封装了抽象工厂模式,抽象工厂是InputSupplier与OutputSupp ...
随机推荐
- ajax和302(转)
原文:http://www.cnblogs.com/dudu/p/ajax_302_found.html 在ajax请求中,如果服务器端的响应是302 Found,在ajax的回调函数中能够获取这个状 ...
- wdatepicker默认时间为当前时间
$(document).ready(function() { alert(today()); document.getElementById("serviceTime").valu ...
- httpclient初步封装
Http通信方式:HttpURLConnection和HttpClient HttpURLConnection是java的标准类,什么都没封装,用起来太原始,不方便HttpClient就是一个增强版的 ...
- HttpServlet Service方法
service() 方法是执行实际任务的主要方法.Servlet 容器(即 Web 服务器)调用 service() 方法来处理来自客户端(浏览器)的请求,并把格式化的响应写回给客户端. 每次服务器接 ...
- Redis学习笔记(1)- CentOS 6.4 安装Redis
Redis学习笔记(1)- CentOS 6.4 安装Redis 2013.10.13 学习环境 vm 10.1 + 默认.新装的干净 CentOS 6.4 64BIT系统 准备 1 ...
- SPOJ11414 COT3 博弈论 + Trie树合并
考虑对于每个子树从下往上依次考虑 对于叶子节点而言,如果可以染色,那么其\(sg\)值为\(1\),否则为\(0\) 考虑往上合并 如果选择了\(x\),那么后继状态就是其所有子树 如果选了其他子树中 ...
- Sed&awk笔记之sed篇(转)
Sed是什么 <sed and awk>一书中(1.2 A Stream Editor)是这样解释的: Sed is a "non-interactive" strea ...
- SWD and JTAG selection mechanism
SWD and JTAG selection mechanism SWJ-DP enables either an SWD or JTAG protocol to be used on the deb ...
- PHPWord 打印 快递单/合同
打印快递单有个特点: 被打印纸的背景是固定的, 你只能 在合适的位置输入快递单的内容,操作步骤如下: 1.制作 word 模板 参考文章 “图解如何用打印机套打快递单” 2.在 模板 中放置“占位符” ...
- DTrace Probes in HotSpot VM
http://docs.oracle.com/javase/6/docs/technotes/guides/vm/dtrace.html