java.io源码解析(四)--字节数组(ByteArrayInputStream,ByteArrayOutputStream)字符数组(CharArrayReader,CharArrayWri...

声明:本系列只供本人自学使用,勿喷。

前面我们已经研究了文件流、对象流,但是前提呢,是需要提供文件、对象才能继续进行流的操作,那假如目前有一个字节数组{0x61, 0x62, 0x63, 0x64, 0x65, 0x66}需要进行传输或者存储到文件,首先得将其转换为二进制流,这时就用到了轻量的ByteArrayInputStream和ByteArrayOutputStream。假如需要操作的是字符数组{'a','b','c','d','e','f'},则要用到CharArrayReader和CharArrayWriter。

一、ByteArrayInputStream

  • 内部有缓冲数组
  • 内部有计数器追踪下一个字节
  • 关闭ByteArrayInputStream后仍然可以对其进行操作。
public class ByteArrayInputStream extends InputStream {
    protected byte buf[];
    protected int pos;
    protected int mark = 0;
    protected int count;

    // 传入的字节数组作为缓冲数组
    public ByteArrayInputStream(byte buf[]) {
        this.buf = buf;
        this.pos = 0;
        this.count = buf.length;
    }

    public ByteArrayInputStream(byte buf[], int offset, int length)
}
  • 核心方法
// 返回下一个字节的值,没有则-1
public synchronized int read()

// copy缓冲区数组buf的未读值到byte b[]中
public synchronized int read(byte b[], int off, int len)
  • 其他方法
public synchronized long skip(long n)
public synchronized int available() 
public boolean markSupported()
public void mark(int readAheadLimit)
public synchronized void reset()

demo

简单操作

        // byte[] byteArray="abcdef".getBytes();
        byte[] byteArray={0x61, 0x62, 0x63, 0x64, 0x65, 0x66};
        ByteArrayInputStream byteArrayInputStream=new ByteArrayInputStream(byteArray);
        int b;
        while ((b=byteArrayInputStream.read())!=-1) {
            System.out.println(b);
        }

实现将Base64图片保存到文件

注:http://imgbase64.duoshitong.com/上传图片生成Base64编码,替换代码第一行content

        String content="data:image/jpeg;base64,/9j/4AAQSkZJRg...省略很长很长..bP6oP/2Q==";
        Pattern pattern= Pattern.compile("data:image/(.*?);base64,");
        Matcher matcher=pattern.matcher(content);
        String type="";
        if(matcher.find()){
            type=matcher.group(1);
        }else{
            return;
        }
        String base64=content.replaceAll(matcher.group(0),"");
        byte[] buffer=new BASE64Decoder().decodeBuffer(base64);
        ByteArrayInputStream bis=new ByteArrayInputStream(buffer);
        // 以下全部代码可以直接用 Files.copy(bis,Paths.get("D:\\test."+type))实现
        OutputStream outputStream= Files.newOutputStream(Paths.get("D:\\test."+type));
        byte[] bytes=new byte[1024];
        int len=0;
        while ((len=bis.read(bytes))!=-1){
            outputStream.write(bytes,0,len);
        }
        outputStream.close();
        bis.close();

二、ByteArrayOutputStream

public class ByteArrayOutputStream extends OutputStream {
    protected byte buf[];
    protected int count;
    
    public ByteArrayOutputStream() {
        this(32);
    }

    public ByteArrayOutputStream(int size){
        buf = new byte[size];
    }

  • 核心方法
// 往buf中写入一个字节
public synchronized void write(int b)
// copy入参 byte b[]到缓冲区数组buf
public synchronized void write(byte b[], int off, int len)

// 将缓冲区数组buf写入其他输出流
public synchronized void writeTo(OutputStream out) throws IOException
// 返回buf
public synchronized byte toByteArray()[] 

public synchronized int size()
public synchronized String toString()

demo

简单操作

byte[] byteArray={0x61, 0x62, 0x63, 0x64, 0x65, 0x66};
ByteArrayOutputStream baos=new ByteArrayOutputStream();
baos.write(byteArray);
baos.write(0x67);
baos.writeTo(Files.newOutputStream(Paths.get("D:\\test.txt")));

CharArrayReader和CharArrayWriter源码过于相似,只是数组是char型,自行查看。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。