javase加强-IO流(二)

本文详细介绍了Java中的字节流、字符流、缓冲流、转换流、数据流、序列化/反序列化以及IO框架,包括FileInputStream/OutputStream、FileReader/FileWriter、BufferedReader/BufferedWriter等,并提及了XML和日志处理在JavaSE中的应用。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

整体学习图

字节流

输入流(读数据)、输出流(写数据)

 FileInputStream读取全部字节

第一步:创建FileInputStream文件字节输入流管道,与源文件接通。
第二步:调用read()方法开始读取文件的字节数据。
第三步:调用close()方法释放资源

// 1、一次性读取完文件的全部字节到一个字节数组中去。
// 创建一个字节输入流管道与源文件接通
InputStream is = new FileInputStream("文件位置");

//2、调用方法读取所有字节,返回一个存储所有字节的字节数组。
byte[] buffer = is.readAllBytes();
System.out.println(new String(buffer));

//3、关闭流
is.close(); 

FileOutputStream写字节

第一步:创建FileOutputStream文件字节输出流管道,与目标文件接通。
第二步:调用wirte()方法往文件中写数据
第三步:调用close()方法释放资源

// 1、创建一个字节输出流管道与目标文件接通。
        // 覆盖管道:覆盖之前的数据
//        OutputStream os =
//                new FileOutputStream("文件位置");

        // 追加数据的管道
        OutputStream os =
                new FileOutputStream("文件位置", true);

        // 2、开始写字节数据出去了
        os.write(97); // 97就是一个字节,代表a
        os.write('b'); // 'b'也是一个字节
        // os.write('李'); // [ooo] 默认只能写出去一个字节

        byte[] bytes = "小李子".getBytes();
        os.write(bytes);

        os.write(bytes, 0, 15);

        // 换行符
        os.write("\r\n".getBytes());

        os.close(); // 关闭流

字节流复制文件

1.需要创建一个FileInputStream流与源文件接通,创建FileOutputStream与目标文件接通
2.然后创建一个数组,使用FileInputStream每次读取一个字节数组的数据,存如数组中
3.然后再使用FileOutputStream把字节数组中的有效元素,写入到目标文件中

 字符流

 如果文件中有中文,使用字节流来读取,就有可能读到半个汉字的情况,这样会导致乱码。

Java专门为我们提供了另外一种流,叫字符流,可以字符流是专门为读取文本数据而生的。  

FileReader类

第一步:创建FileReader对象与要读取的源文件接通
第二步:调用read()方法读取文件中的字符
第三步:调用close()方法关闭流

try (
                // 1、创建一个文件字符输入流管道与源文件接通
                Reader fr = new FileReader("文件位置");
                ){

            // 2、每次读取多个字符。(性能是比较不错的!)
            char[] buffer = new char[3];
            int len; // 记住每次读取了多少个字符。
            while ((len = fr.read(buffer)) != -1){
                // 读取多少倒出多少
                System.out.print(new String(buffer, 0, len));
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

FileWriter类

第一步:创建FileWirter对象与要读取的目标文件接通
第二步:调用write(字符数据/字符数组/字符串)方法读取文件中的字符
第三步:调用close()方法关闭流

try (
                // 0、创建一个文件字符输出流管道与目标文件接通。
                // 覆盖管道
                // Writer fw = new FileWriter("文件位置");
                // 追加数据的管道
                Writer fw = new FileWriter("文件位置", true);
                ){
            // 1、public void write(int c):写一个字符出去
            fw.write('a');
            fw.write(97);
            fw.write("\r\n"); // 换行

            // 2、public void write(String c)写一个字符串出去
            fw.write("kussmcx");
            fw.write("\r\n");

            // 3、public void write(String c ,int pos ,int len):写字符串的一部分出去
            fw.write("小李子", 0, 5);
            fw.write("\r\n");

            // 4、public void write(char[] buffer):写一个字符数组出去
            char[] buffer = {'黑', '马', 'a', 'b', 'c'};
            fw.write(buffer);
            fw.write("\r\n");

            // 5、public void write(char[] buffer ,int pos ,int len):写字符数组的一部分出去
            fw.write(buffer, 0, 2);
            fw.write("\r\n");
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

缓冲流

缓冲流的作用:可以对原始流进行包装,提高原始流读写数据的性能。

缓冲字节流

 try (
                InputStream is = new FileInputStream("文件位置");
                // 1、定义一个字节缓冲输入流包装原始的字节输入流
                InputStream bis = new BufferedInputStream(is);

                OutputStream os = new FileOutputStream("文件位置");
                // 2、定义一个字节缓冲输出流包装原始的字节输出流
                OutputStream bos = new BufferedOutputStream(os);
        ){

            byte[] buffer = new byte[1024];
            int len;
            while ((len = bis.read(buffer)) != -1){
                bos.write(buffer, 0, len);
            }
            System.out.println("复制完成!!");

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

字符缓冲流

reader

 try (
                Reader fr = new FileReader("io-app2\\src\\itheima04.txt");
                // 创建一个字符缓冲输入流包装原始的字符输入流
                BufferedReader br = new BufferedReader(fr);
        ){

            String line; // 记住每次读取的一行数据
            while ((line = br.readLine()) != null){
                System.out.println(line);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

writer

 try (
                Writer fw = new FileWriter("io-app2/src/itheima05out.txt", true);
                // 创建一个字符缓冲输出流管道包装原始的字符输出流
                BufferedWriter bw = new BufferedWriter(fw);
        ){

            bw.write('李');
            bw.newLine();//换行

            bw.write("小李子");
            bw.newLine();

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

转换流

Java给我们提供了另外两种流InputStreamReader,OutputStreamWriter,这两个流我们把它叫做转换流。它们可以将字节流转换为字符流,并且可以指定编码方案。

InputStreamReader类

InputStreamReader也是不能单独使用的,它内部需要封装一个InputStream的子类对象,再指定一个编码表,如果不指定编码表,默认会按照UTF-8形式进行转换。

try (
                // 1、得到文件的原始字节流(GBK的字节流形式)
                InputStream is = new FileInputStream("文件位置");
                // 2、把原始的字节输入流按照指定的字符集编码转换成字符输入流
                Reader isr = new InputStreamReader(is, "GBK");//默认是UTF-8
                // 3、把字符输入流包装成缓冲字符输入流
                BufferedReader br = new BufferedReader(isr);
                ){
            String line;
            while ((line = br.readLine()) != null){
                System.out.println(line);
            }


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

OutputStreamWriter类

OutputStreamReader也是不能单独使用的,它内部需要封装一个OutputStream的子类对象,再指定一个编码表,如果不指定编码表,默认会按照UTF-8形式进行转换。

try (
                // 1、创建一个文件字节输出流
                OutputStream os = new FileOutputStream("文件位置");
                // 2、把原始的字节输出流,按照指定的字符集编码转换成字符输出转换流。
                Writer osw = new OutputStreamWriter(os, "GBK");
                // 3、把字符输出流包装成缓冲字符输出流
                BufferedWriter bw = new BufferedWriter(osw);
                ){
            bw.write("输入的文字字符");

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

打印流

一般会使用打印流特有的方法叫`print(数据)`或者`println(数据)`,它打印啥就输出啥。

打印流有两个,一个是字节打印流PrintStream,一个是字符打印流PrintWriter

 // 1、创建一个打印流管道
//                PrintStream ps =
//                        new PrintStream("文件位置", Charset.forName("GBK"));
//                PrintStream ps =
//                        new PrintStream("文件位置");
                PrintWriter ps =
                        new PrintWriter(new FileOutputStream("文件位置", true));
                ){
                ps.print(97);	//文件中显示的就是:97

                ps.write(97); //文件中显示a

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

重定向输出语句

System.out.println()这句话表示打印输出,可以往控制台打印输出任意类型的数据

System还提供了一个方法,可以修改底层的打印流,这样我们就可以重定向打印语句的输出目的地了。

        System.out.println("输入的字符");
       

        try ( PrintStream ps = new PrintStream("文件位置"); ){
            // 把系统默认的打印流对象改成自己设置的打印流
            System.setOut(ps);

            
            System.out.println("输入的字符");
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

数据流(用的不多)

我们想把数据和数据的类型一并写到文件中去,读取的时候也将数据和数据类型一并读出来。

DataOutputStream类

try (
                // 1、创建一个数据输出流包装低级的字节输出流
                DataOutputStream dos =
                        new DataOutputStream(new FileOutputStream("文件位置"));
                ){
            dos.writeInt(97);//int类型
            dos.writeDouble(99.5);//double类型
            dos.writeBoolean(true);//boole类型
            dos.writeUTF("小李子");//字符类型

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

 DataInputStream类

try (
                DataInputStream dis =
                        new DataInputStream(new FileInputStream("文件位置"));
                ){
            int i = dis.readInt();//读int类型
            System.out.println(i);

            double d = dis.readDouble();//读double类型
            System.out.println(d);

            boolean b = dis.readBoolean();//读Boolean类型
            System.out.println(b);

            String rs = dis.readUTF();//读文字类型
            System.out.println(rs);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

序列化流

序列化:意思就是把对象写到文件或者网络中去。(简单记:写对象)
反序列化:意思就是把对象从文件或者网络中读取出来。(简单记:读对象)

ObjectOutputStraem类

// 注意:对象如果需要序列化,必须实现序列化接口。
public class User implements Serializable  {}

try (
//1、创建一个user类对象
// 2、创建一个对象字节输出流包装原始的字节 输出流。
                ObjectOutputStream oos =
                        new ObjectOutputStream(new FileOutputStream("文件位置"));
                ){
            // 1、创建一个Java对象。
            User u = new User("admin", "张三", 32, "666888xyz");

            // 3、序列化对象到文件中去
            oos.writeObject(u);
            System.out.println("序列化对象成功!!");

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

ObjectInputStream类

文件中已经有一个Student对象,现在要使用ObjectInputStream读取出来。称之为反序列化。

 try (
            // 1、创建一个对象字节输入流管道,包装 低级的字节输入流与源文件接通
            ObjectInputStream ois = new ObjectInputStream(new FileInputStream("文件位置"));
        ){
            User u = (User) ois.readObject();
            System.out.println(u);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

IO框架

由apache开源基金组织提供了一组有关IO流小框架,可以提高IO流的开发效率。

其本质是别人写好的一些字节码文件(class文件),打包成了一个jar包。我们只需要把jar包引入到我们的项目中,就可以直接用了。 

下一篇

javase加强--XML和日志-优快云博客

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值