IO流基础笔记

IO流

什么是IO流?

​ IO流也称为输入、输出流,就是用来读写数据的。

  • I:表示input,是数据从硬盘读入到内存中的过程,称为输入,负责读

  • O:表示output,是内存程序的数据从内存到硬盘的过程,称之为输出,负责写。

    I: 硬盘→→内存(读入) O:内存→→硬盘(读出)

IO流的分类

方向分 输入流 输出流

按数据最小单位分 字节流 字符流

字节流 更适合 读写 —— 音视频文件

字符流 更适合读写 —— 文本内容

IO流的体系

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-X6bu5Fvi-1677152619915)(D:\JAVA笔记(第一遍)\assets\1673509259137.png)]

字节输入流 —FileInputStream

一、单字节读取

​ 1、创建一个文件字节输入流管道,与源文件连通

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ZeLOFGvO-1677152619916)(D:\JAVA笔记(第一遍)\assets\1673510319527.png)]

//        创建一个文件字节输入流管道 ,与源文件连接
        InputStream is = new FileInputStream("file-io-app\\src\\date");

​ 2、读取一个字节并返回

//        读取一个字节返回
        int b1 = is.read();
        System.out.println((char) b1);
        int b2 = is.read();  // 长度
        System.out.println((char) b2);

​ 3、使用循环读取所有字节

  // 循环不能读取中文字符,会乱码,因为每次只读取一个字节,中文字符在UTF-8中占三个字节 
		int n ;
        while ((n = is.read())!=-1){
            System.out.println(n);
        }

没有字节可读,则返回-1

public int read();  // 每次读取一个字节,如果字节没有则返回 -1

单字节读取弊端:

  • 性能较慢
  • 读取中文出现乱码现象

二、数组字节读取

​ 1、创建一个文件字节输入流管道,与源文件连通

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-c7ANUazX-1677152619916)(D:\JAVA笔记(第一遍)\assets\1673513652772.png)]

//        创建一个文件字节输入流管道 ,与源文件连接
        InputStream is = new FileInputStream("file-io-app\\src\\date");

​ 2、定义一个数组,用于读取字节

//        定义一个数组,用于读取字节数组
        byte[] buffer = new byte[3];
        int len = is.read(buffer);    //每次读取的字节个数
        System.out.println(len);
//       解码
        String rs = new String(buffer);
        System.out.println(rs);

​ 3、使用循环读取所有字节

        int len;   //     记录每次读取的字节数
// 		相当于一个长度为3的容器   是 byte 类型的
        byte[] buffer = new byte[3];   
        while ((len = is.read(buffer)) != -1) {
// 读取多少倒出多少  String sc = new String (byte[] , 开始位置 , 结束位置 );
        System.out.println(new String(buffer,0,len));
        }

总结 :

①磁盘跟内存连同

②创造一个有容器

③每次从内存中装入设定容器大小的数据

④解码输出

三、定义数组与文件相同

自定义总结:

​ 定义一个数组,大小和文件大小一致,这样就不会出现乱码情况

①先拿到文件大小

File f = new File("file-io-app\\src\\date2");
 System.out.println(f.length());

②创建流通管道

     InputStream is = new FileInputStream(f);

③创建一个跟文件大小一样的数组

      byte[] buffer = new byte[(int) f.length()];

④ 解码并输出

        String rs = new String(buffer);
        System.out.println(rs);
官方API
//      读取所有字节
        byte[] bytes = is.readAllBytes();
//      解码
        String sc = new String(bytes);
        System.out.println(sc);

字节输出流—FileOutputStream

一、基本写法

创建字节文件输出管道,与目标文件连通

  OutputStream os = new FileOutputStream( "file-io-app/src/out04.txt",true);
//true 代表append,不加直接覆盖重新写,加上代表接着写
1、单个字节写进去
       os.write(98);
       os.write(97);
       os.write(99);
       os.write(100);
2、数组写进去
byte[] bytes = {102,103};     
os.write(bytes);
3、中文写进去
//        中文可以解码写进去
        String name = "我和你子啊一起";
        byte[] bytes1 = name.getBytes();
        os.write(bytes1);
4、可以写一部分进去
byte[] bytes3 = {102,103,97,98,99};
os.write(bytes,0,3);

二、自我总结

①换行

os.write("\r\n".getBytes());

②写完必须刷新

os.flush();

③用完流要关闭

os.close();

④关闭可以自动刷新

拷贝文件

一、自己思路

①创建一个输入流管道,负责读取源文件的数据

InputStream is = new FileInputStream("D:\\JAVA\\文件名.mp4");

②创建一个输出流管道,负责写入目标文件的数据

OutputStream os = new FileOutputStream("D:\\JAVA\\newMov.mp4");

③定义一个数组,负责转移数据(中转站)

byte[] buffer = new byte[1024];
int len;// 记录每次读取的字节数,用于最后装不满,导致数据错误

④开是运转,读数据→放数组中→写到目的地 (读→中转→写)

//       4、 从源文件中读取数据,并装入数组中       
while ((len = is.read(buffer)) != -1) {//         
   // 5、数组中的数据写入到目标文件中         
        os.write(buffer, 0, len);     
}

⑤最后,先关闭输出流 ,再关闭输入流

os.close();
is.close();

二、整体代码

package com.maoteng.d4_byte_stream;

import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;

public class CopyDemo5 {
    public static void main(String[] args) throws Exception {
//       1、 创建一个字节输入流管道与源文件连通
        InputStream is = new FileInputStream("D:\\JAVA\\17、总结:数据类型、运算符.mp4");

//        2、创建一个字节输出流管道与目标文件连通
        OutputStream os = new FileOutputStream("D:\\JAVA\\newMov.mp4");

//        3、定义一个数组,负责转移(中转站)
        byte[] buffer = new byte[1024];
        int len;// 记录每次读取的字节数,用于最后装不满,导致数据错误

//       4、 从源文件中读取数据,并装入数组中
        while ((len = is.read(buffer)) != -1) {
//          5、数组中的数据写入到目标文件中
            os.write(buffer, 0, len);
        }
        System.out.println("复制完成");
        os.close();
        is.close();
    }
}

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-cT3PMrow-1677152619917)(D:\JAVA笔记(第一遍)\assets\1673518651351.png)]

三、易错点

单字节读取,int b1 接收的是字节

int b1 = is.read();
System.out.println(b1);

数组读取 , int len 接收的是字节数

byte[] buffer = new byte[1024];
int len;// 记录每次读取的字节数,用于最后装不满,导致数据错误

资源释放

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-6FddiyH2-1677152619917)(D:\JAVA笔记(第一遍)\assets\1673576654158.png)]

一、手动释放

1、格式
 try {
     // 易错代码体
        } catch (Exception e) {
     // 打印错误信息
            e.printStackTrace();
        } finally {
     // 肯定回执行的代码体,一般是释放资源   
     //  实现(implements)  closeable接口的是资源
     public abstract class OutputStream implements Closeable {
        }
 }

二、自动释放资源①

1、格式
       //  资源文件    实现(implements)  closeable接口的是资源    
		try (资源文件,用完自动释放) {
              // 易错代码体
        } catch (Exception e) {
               // 打印错误信息
            e.printStackTrace();
        }

二、自动释放资源②

1、格式
public static void main(String[] args) throws Exception {
		InputStream is = new FileInputStream("地址");// 资源文件
		OutputStream os = new FileOutputStream("地址");// 资源文件
        try (is; os) {
          // 易错代码体
          // 可以直接使用  is   os
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

自动释放②缺点 :异常信息必须要抛出,不能try catch ,否则下面又访问不了。

字符流

一、字符输入流

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-6Qq92vsl-1677152619917)(D:\JAVA笔记(第一遍)\assets\1673578946656.png)]

1、单字节读取

1、创建一个字符输入管道,与源文件对象连通

        Reader reader = new FileReader("file-io-app\\src\\out04.txt");

2、读取字符

		int read = reader.read();

3、转成字符形式展现

		System.out.println((char) read);

4、用循环展现全部

            int len;
            while ((len = reader.read())!=-1){
                System.out.print((char) len);
            }

整体代码

package com.maoteng.d6_char_stream;

import java.io.FileReader;
import java.io.Reader;

public class CharStream01 {
    /*
     *           读取一个字符
     */
    public static void main(String[] args) {
//         1、 创建一个字符输入管道,与源文件对象连通
        try {
            Reader reader = new FileReader("file-io-app\\src\\out04.txt");
//        2、读取字符
          int read = reader.read();
//         3、转成字符形式展现
            System.out.println((char) read);
//          4  用循环读取全部
            int len;
            while ((len = reader.read())!=-1){
                System.out.print((char) len);
            }

        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

2、数组读取

1、创建一个字符输入管道,与源文件对象连通

        Reader reader = new FileReader("file-io-app\\src\\out04.txt");

2、定义一个数组,用于存放数据

char[] buffer = new char[1024];

3、定义一个变量,记录每次读取的个数

int len;

4、利用循环,开始读取数据,并放入数组中

 while ((len = reader.read(buffer))!=-1){
//                5  进行解码
                String  rs = new String(buffer,0,len);
                System.out.print(rs);
            }

整体代码

package com.maoteng.d6_char_stream;

import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.Reader;
import java.util.Date;

public class CharStream02 {
    /*
     *          数组读取字符
     */
    public static void main(String[] args) {
        try {
            Date date = new Date();
            System.out.println(date.getTime());
//         1、 创建一个字符输入管道,与源文件对象连通
            Reader reader = new FileReader("file-io-app\\src\\out04.txt");
//         2 定义一个数组用于存放接收的数据
            char[] buffer = new char[1024];
//         3  定义一个长度,记录每次读取的个数
            int len;
//            4  利用循环开始读取数据  读到的数据放在 buffer里面
            while ((len = reader.read(buffer))!=-1){
//                5  进行解码
                String  rs = new String(buffer,0,len);
                System.out.print(rs);
            }
            Date date1 = new Date();
            System.out.println(date1.getTime());

        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

二、字符输出流

1、创建一个字符输出流,与目标文件连通

Writer fw = new FileWriter("file-io-app/src/date5.txt",true);

2、写一个字符

           	fw.write('a');
           	fw.write('1');
            fw.write("\r\n");
            fw.write('我');

3、写一个字符串

fw.write("我和你子啊一起");

4、写一个字符数组

char[] chars = {'a','b','c'};

5、写字符串的一部分

fw.write("我爱你憨憨",0,3);

6、字符数组的一部分

fw.write(chars,0,2);

7、刷新关闭流

//            刷新流
            fw.flush();
//            关闭流
            fw.close();

整体代码

package com.maoteng.d6_char_stream;

import java.io.FileWriter;
import java.io.IOException;
import java.io.Writer;

public class CharStream03 {
//    文件字符输出流,写数据方法
    public static void main(String[] args) {
//        创建一个字符输出流,与目标文件连通
        try {
            Writer fw = new FileWriter("file-io-app/src/date5.txt",true);
            //              写一个字符
                fw.write('a');
                fw.write('1');
            fw.write("\r\n");
            fw.write('我');
//              写一个字符串
            fw.write("我和你子啊一起");
//            写一个字符数组
            char[] chars = {'a','b','c'};
            fw.write(chars);
            fw.write("\r\n");
//            写一个字符串的一部分
            fw.write("我爱你憨憨",0,3);
//            写一个字符数组的一部分
            fw.write(chars,0,2);
            fw.write("\r\n");
//            刷新流
            fw.flush();
//            关闭流
            fw.close();

        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

个人总结

字节流

​ ① 更适合一切文件数据的拷贝——音视频、文本

​ ② 字节流不适合中文内容的输出,容易出现乱码现象

字符流

① 更适合做文本文件的操作(读 、写)

        fw.write("我和你子啊一起");

// 写一个字符数组
char[] chars = {‘a’,‘b’,‘c’};
fw.write(chars);
fw.write(“\r\n”);
// 写一个字符串的一部分
fw.write(“我爱你憨憨”,0,3);
// 写一个字符数组的一部分
fw.write(chars,0,2);
fw.write(“\r\n”);
// 刷新流
fw.flush();
// 关闭流
fw.close();

    } catch (IOException e) {
        e.printStackTrace();
    }
}

}


#### 个人总结 

字节流 

​		① 更适合一切文件数据的拷贝——音视频、文本	

​		② 字节流不适合中文内容的输出,容易出现乱码现象



字符流

 	① 更适合做文本文件的操作(读 、写)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值