IO知识点汇总2
7、SequenceInputStream 合并流
可以把两个及两个以上的InputStream合并,提供两个构造方法
这里说下Enumeration接口,这个和Iterator类似,不过只提供遍历Vector和HashTable集合的功能,且不能移除元素。
Vector<InputStream> vector = new Vector<>(); vector.add(new FileInputStream(path + "1.txt")); vector.add(new FileInputStream(path + "2.txt")); vector.add(new FileInputStream(path + "3.txt")); Enumeration<InputStream> enumeration = vector.elements(); SequenceInputStream in = new SequenceInputStream(enumeration); OutputStream out = new BufferedOutputStream(new FileOutputStream(path + "result.txt")); byte[] bytes = new byte[1024]; int i = 0; while ((i = in.read(bytes)) != -1) { out.write(bytes, 0, i); }
使用的时候,就把流放到Vector中,然后转成Enumeration放到SequenceInputStream中,后续正常读流的操作。
8、PipedInputStream和PipedOutputStream
这两个平常可能不常见,需要两个配合使用,两个互相是彼此的构造方法的参数,或者也可以通过connect方法连接彼此。
PipedInputStream的read方法是阻塞的,等着PipedOutputStream写入数据或PipedOutputStream关闭。
看了源码,基本就是PipedOutputStream写入的时候,调用PipedInputStream的recive方法,将数据传给输入流来实现线程间通信。
public class PipedInputThread extends Thread { InputStream in; public PipedInputThread(PipedInputStream in) { this.in = in; } @Override public void run() { try { System.out.println("接收数据中~~~"); byte[] bytes = new byte[1024]; int len = 0; while ((len = in.read(bytes)) != -1) { System.out.println("input receive:" + new String(bytes, 0, len)); } System.out.println("over!……"); } catch (Exception e) { e.printStackTrace(); } finally { IOUtils.closeQuietly(in); } } }
public class PipedOutputThread extends Thread { OutputStream out; public PipedOutputThread(PipedOutputStream out) { this.out = out; } @Override public void run() { try { System.out.println("准备写入数据!……"); Thread.sleep(6000); for (int i = 0; i < 10; i++) { out.write(("hello world" + i).getBytes()); } System.out.println("write over!……"); } catch (Exception e) { e.printStackTrace(); } finally { IOUtils.closeQuietly(out); } } }
public class TestPipedStream { public static void testPipedStream() { try { PipedOutputStream out = new PipedOutputStream(); PipedInputStream in = new PipedInputStream(out); Thread inputThread = new PipedInputThread(in); Thread outputThread = new PipedOutputThread(out); inputThread.start(); outputThread.start(); } catch (IOException e) { e.printStackTrace(); } } public static void main(String[] args) { testPipedStream(); } }
可以参照上面例子来掌握其使用方法。
9、ByteArrayInputStream和ByteArrayOutputStream
通过名字我们就可以看出,这个读写的对象是字节数组,像FileInputStream和FileOutputStream读写的对象就是文件。
ByteArrayOutputStream可能比较常见,多用在缓存数据,其缓冲区可以自动增长,当写入完成时可以提取全部数据
FileInputStream fileInputStream = new FileInputStream(path + "result.txt"); BufferedInputStream bufferedInputStream = new BufferedInputStream(fileInputStream); ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); int len; byte[] bytes = new byte[1024]; while ((len = bufferedInputStream.read(bytes)) != -1) { byteArrayOutputStream.write(bytes, 0, len); } byte[] arr = byteArrayOutputStream.toByteArray();
ByteArrayInputStream没想到有什么使用场景,以后碰到了可以在深入理解,现在看到的优势可能就是关闭流以后缓冲的数据还在吧。
ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream(arr); while ((len = byteArrayInputStream.read(bytes)) != -1) { System.out.println(new String(bytes, 0, len)); }