缓冲流、转换流、数据处理流、序列化

一、缓冲流

1.概述

缓冲流,也叫高效流,是对4个基本的FileXxx 流的增强,所以也是4个流,按照数据类型分类:

  • 字节缓冲流BufferedInputStreamBufferedOutputStream
  • 字符缓冲流BufferedReaderBufferedWriter

缓冲流的基本原理,是在创建流对象时,会创建一个内置的默认大小的缓冲区数组,通过缓冲区读写,减少系统IO次数,从而提高读写的效率。

2.字节缓冲流

1) 构造方法

  • public BufferedInputStream(InputStream in) :创建一个 新的缓冲输入流。
  • public BufferedOutputStream(OutputStream out): 创建一个新的缓冲输出流。

构造举例,代码如下:

// 创建字节缓冲输入流
BufferedInputStream bis = new BufferedInputStream(new FileInputStream("bis.txt"));
// 创建字节缓冲输出流
BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream("bos.txt"));

字节缓冲输入流:

public class Demo015IO {
    public static void main(String[] args)throws Exception {
		
        File file = new File("aaa.txt");

        InputStream is = new FileInputStream(file);
		//BufferedInputStream方法中传入的是InputStream
        BufferedInputStream bis = new BufferedInputStream(is);

        byte[] bs = new byte[1024];

        int len ;
        while((len=bis.read(bs))!=-1){
            System.out.println(new String(bs,0,len,"UTF-8"));
        }

        bis.close();
        is.close();
    }
}

2)效率测试

节点流慢,缓冲流快!

public class BufferedDemo {
    public static void main(String[] args) throws FileNotFoundException {
      	// 记录开始时间
        long start = System.currentTimeMillis();
		// 创建流对象
        try (
			BufferedInputStream bis = new BufferedInputStream(new FileInputStream("jdk9.exe"));
		 BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream("copy.exe"));
        ){
          	// 读写数据
            int len;
            byte[] bytes = new byte[8*1024];
            while ((len = bis.read(bytes)) != -1) {
                bos.write(bytes, 0 , len);
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
		// 记录结束时间
        long end = System.currentTimeMillis();
        System.out.println("缓冲流使用数组复制时间:"+(end - start)+" 毫秒");
    }
}
缓冲流使用数组复制时间:666 毫秒

3.字符缓冲流

1)构造方法

  • public BufferedReader(Reader in) :创建一个 新的缓冲输入流。
  • public BufferedWriter(Writer out): 创建一个新的缓冲输出流。

构造举例,代码如下:

// 创建字符缓冲输入流
BufferedReader br = new BufferedReader(new FileReader("br.txt"));
// 创建字符缓冲输出流
BufferedWriter bw = new BufferedWriter(new FileWriter("bw.txt"));

2)特有方法

字符缓冲流的基本方法与普通字符流调用方式一致,不再阐述,我们来看它们具备的特有方法。

  • BufferedReader:public String readLine(): 读一行文字。
  • BufferedWriter:public void newLine(): 写一行行分隔符,由系统属性定义符号。

字符缓冲输入流:

/**
 * 字符缓冲流  BufferedRerader
 */
public class Demo016IO {
    public static void main(String[] args) throws Exception {
        File file = new File("aaa.txt");
        
        Reader r = new FileReader(file);
        
        BufferedReader br = new BufferedReader(r);
        
        String str;
        //readline  读一行
        while((str = br.readLine())!=null){
            System.out.println(str);
        }
        br.close();
    	r.close();
    }
}

字符缓冲输出流:

/**
 * 写出去
 */
public class Demo017IO {
    public static void main(String[] args) throws Exception{
        File file = new File("suibian.txt");
        Writer w = new FileWriter(file);
        BufferedWriter bw = new BufferedWriter(w);

        bw.write("随便写,不用敲,好开心");
        bw.newLine();

        bw.flush();
        bw.close();
        w.close();
    }
}

二、转换流

1.字符编码和字符集

按照某种规则,将字符存储到计算机中,称为编码 。反之,将存储在计算机中的二进制数按照某种规则解析显示出来,称为解码 。当编码和解码所用的字符集不同时,就会发生乱码!

2.常见字符集

在这里插入图片描述

3.InputStreamReader类

1)构造方法

  • InputStreamReader(InputStream in): 创建一个使用默认字符集的字符流。
  • InputStreamReader(InputStream in, String charsetName): 创建一个指定字符集的字符流。

构造举例,代码如下:

InputStreamReader isr = new InputStreamReader(new FileInputStream("in.txt"));
InputStreamReader isr2 = new InputStreamReader(new FileInputStream("in.txt") , "GBK");

2)指定编码读取

public class ReaderDemo2 {
    public static void main(String[] args) throws IOException {
      	// 定义文件路径,文件为gbk编码
        String FileName = "E:\\file_gbk.txt";
      	// 创建流对象,默认UTF8编码
        InputStreamReader isr = new InputStreamReader(new FileInputStream(FileName));
      	// 创建流对象,指定GBK编码
        InputStreamReader isr2 = new InputStreamReader(new FileInputStream(FileName) , "GBK");
		// 定义变量,保存字符
        int read;
      	// 使用默认编码字符流读取,乱码
        while ((read = isr.read()) != -1) {
            System.out.print((char)read); // ��Һ�
        }
        isr.close();
      
      	// 使用指定编码字符流读取,正常解析
        while ((read = isr2.read()) != -1) {
            System.out.print((char)read);// 大家好
        }
        isr2.close();
    }
}

4.OutputStreamWriter类

1)构造方法

  • OutputStreamWriter(OutputStream in): 创建一个使用默认字符集的字符流。
  • OutputStreamWriter(OutputStream in, String charsetName): 创建一个指定字符集的字符流。

构造举例,代码如下:

OutputStreamWriter isr = new OutputStreamWriter(new FileOutputStream("out.txt"));
OutputStreamWriter isr2 = new OutputStreamWriter(new FileOutputStream("out.txt") , "GBK");

2)指定编码写出

public class OutputDemo {
    public static void main(String[] args) throws IOException {
      	// 定义文件路径
        String FileName = "E:\\out.txt";
      	// 创建流对象,默认UTF8编码
        OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream(FileName));
        // 写出数据
      	osw.write("你好"); // 保存为6个字节
        osw.close();
      	
		// 定义文件路径
		String FileName2 = "E:\\out2.txt";
     	// 创建流对象,指定GBK编码
        OutputStreamWriter osw2 = new OutputStreamWriter(new FileOutputStream(FileName2),"GBK");
        // 写出数据
      	osw2.write("你好");// 保存为4个字节
        osw2.close();
    }
}

三、数据处理流

可以处理基本类型+String,保留数据的类型。前提是读取顺序与写出顺序一致,否则读取数据不正确

/**
 * 放入一个int类型的1到文件中
 */
public class DataIOStream {
    public static void main(String[] args)throws Exception {
        int i = 980;
        // 文件
        File file = new File("F:\\输入输出流\\data.txt");
        DataOutputStream dos = new DataOutputStream(new FileOutputStream(file));

        // 写出一个整数
        dos.writeInt(i);//   ?
        dos.flush();
        dos.close();

        //读
        DataInputStream dis = new DataInputStream(new FileInputStream(file));
        int a = dis.readInt();
        System.out.println(a*2);//1960
        dis.close();
    }
}

四、序列化

Java 提供了一种对象序列化的机制。用一个字节序列可以表示一个对象,该字节序列包含该对象的数据对象的类型对象中存储的属性等信息。字节序列写出到文件之后,相当于文件中持久保存了一个对象的信息。

反之,该字节序列还可以从文件中读取回来,重构对象,对它进行反序列化

1.ObjectOutputStream类

1)构造方法

  • public ObjectOutputStream(OutputStream out): 创建一个指定OutputStream的ObjectOutputStream。
FileOutputStream fileOut = new FileOutputStream("employee.txt");
ObjectOutputStream out = new ObjectOutputStream(fileOut);

2)序列化操作

  1. 一个对象要想序列化,必须满足两个条件:
  • 该类必须实现java.io.Serializable 接口,Serializable 是一个标记接口,不实现此接口的类将不会使任何状态序列化或反序列化,会抛出NotSerializableException
  • 该类的所有属性必须是可序列化的。如果有一个属性不需要可序列化的,则该属性必须注明是瞬态的,使用transient 关键字修饰。

2.ObjectInputStream类

1)构造方法

  • public ObjectInputStream(InputStream in): 创建一个指定InputStream的ObjectInputStream。

代码演示:

public class Person implements Serializable {
    private String name;
    private int age;
    private boolean gender;

    public Person() {
    }

    public Person(String name, int age, boolean gender) {
        this.name = name;
        this.age = age;
        this.gender = gender;
    }

    @Override
    public String toString() {
        return "Person{" +
                "name='" + name + '\'' +
                ", age=" + age +
                ", gender=" + gender +
                '}';
    }
}

序列化与反序列化:

public class PersonSerializable {
    public static void main(String[] args)throws Exception {
        // 对象
        Person p = new Person("张三",20,true);
        // 文件
        File file = new File("F:\\输入输出流\\objFile.txt");
        // 原始的输出流
        OutputStream os = new FileOutputStream(file);
        // 处理流  序列化
        ObjectOutputStream ots = new ObjectOutputStream(os);
        ots.writeObject(p);//输出的是看不懂的东西,但程序能看懂
        ots.flush();
        ots.close();
        os.close();

        //读  反序列化
        ObjectInputStream ois = new ObjectInputStream(new FileInputStream(file));
        Object obj = ois.readObject();
        System.out.println(obj);//Person{name='张三', age=20, gender=true}
        ois.close();
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值