javaIO流(2)

news2024/12/23 2:47:29

一.字符流

字符流对数据的操作是以一个个字符为单位的,字符流只能读文本文件,并将读到的字节按照编码表转为对应的字符,Reader和Writer是字符流的两个最大的抽象类,InputStreamReader和OutputStreamWriter分别继承了Reader和Writer,它俩的功能就是将读取到的字节转换为字符,所以又被称为转换流

1. FileReader和FileWriter读写文件

FileReader常用方法方法阐述
FileReader(String fileName)构造方法,用来指定要读的文件
int read()读取一个字符,返回读到的字符的码值,如果读到-1则表示读取完毕
int read(char[] chars)一次读一个字符数组,返回实际读取到的字符个数

FileWriter常用方法方法阐述
FileWriter(String fileName,boolean append)构造方法,用来指定要写入的文件,并且可以设置是追加,还是覆盖当前内容
void writer(int c)一次写一个字符
void writer(char[] chars,in off,int len)一次写一个字符数组,从字符数组的off位置开始,写len个

1.1  一个字符一个字符读

public class CharDemo1 {
    public static void main(String[] args) throws IOException {

        /*
        字符流只能读文本文件,会将读到字节结合编码表转换为一个字符编码
         */

        //一次读一个字符

        FileReader fileReader = new FileReader("E:/demo.txt");
        FileWriter fileWriter = new FileWriter("E:/demo1.txt");
        int c = 0;
        while((c = fileReader.read())!=-1){
            fileWriter.write(c);
        }
        fileReader.close();
        fileWriter.close();
    }
}

1.2  一次读一个字符数组

public class CharDemo2 {
    public static void main(String[] args) throws IOException {


        /*
        字符流只能读文本文件,会将读到字节结合编码表转换为一个字符编码
         */


        //一次读一个char数组
        FileReader fileReader = new FileReader("E:/demo.txt");
        FileWriter fileWriter = new FileWriter("E:/demo1.txt");
        int size = 0;
        char[] chars = new char[10];
        while((size = fileReader.read(chars))!=-1){
            fileWriter.write(chars,0,size);
        }
        fileReader.close();
        fileWriter.close();
    }
}

2. 字符缓冲流(包装流)

BufferedReader常用方法方法阐述
BufferedReader(Reader in)构造方法,可以传入一个Reader类对象
String readLine()一次读一行数据

BufferedWrite常用方法方法阐述
BufferedWriter(Writer our)构造方法,可以传一个Writer类对象
void write(String s)一次写一个字符串
void newLine()写一个换行符

2.1 BufferedReader和BufferedWriter读写文件

BufferReader和BufferWriter是两个包装流,可以对节点流FileReader和FileWriter进行包装,支持一次读写一行数据大大提高了数据的读写效率,FileWriter的构造方法中可以增加一个布尔类型的参数,表示写入文件的内容不会覆盖原内容,而是追加到文件原有内容的后面,bufferWriter中的newLine()方法表示写入一个换行符到文件中

public class CharDemo3 {
    /*
    字符流只能读文本文件,会将读到字节结合编码表转为一个字符编码
     */

    public static void main(String[] args) throws IOException {
        FileReader fileReader = new FileReader("E:/demo.txt");
        FileWriter fileWriter = new FileWriter("E:/demo1.txt",true);//保留原来的内容,在原内容基础上向后追加(续写)
        BufferedReader bufferedReader = new BufferedReader(fileReader);
        BufferedWriter bufferedWriter = new BufferedWriter(fileWriter);
        String s = null;
        while((s=bufferedReader.readLine())!=null){
            bufferedWriter.write(s);
            bufferedWriter.newLine();//插入换行符
        }
        bufferedReader.close();
        bufferedWriter.close();
    }
}

2.2  BufferReader从控制台读取数据

public class CharDemo4 {
    public static void main(String[] args) throws IOException {
        /*
          利用BufferReader从控制台读取内容
     */

        BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(System.in));
        System.out.println("请输入字符串");
        String s = bufferedReader.readLine();
        System.out.println(s);
    }

}

二.  对象输入输出字节流

对象输入流(ObjectInputStream):从文件中把对象输入到程序中

对象输出流(ObjectOutputStream):把java中的对象输出到文件中

这两个属于包装流,可以对字节输入流和字节输出流进行包装处理

1. 为什么要把对象输入到文件中

这是因为我们在程序中new的对象都存在内存中,当程序运行结束后,对象会随着销毁,无法做到将对象的信息永久保存,但有时我们有这种将对象信息永久保存的需求,在需要的时候在还原到程序中.

例如:平时一个游戏凌晨更新维护的时候,往往需要关闭服务器,那我们玩家的账号信息肯定要保存下来,等到维护完成,再将数据恢复到相应的玩家账号中

2. 对象的序列化和反序列化

对象的序列化:将对象信息从程序写到文件中保存

对象的反序列化:将对象信息从文件读到程序中

对象的序列化通过对象输出流来实现(ObjectOutputStream)

ObjectOutputStream常用方法方法阐述
ObjectOutputStream(OutputStream out)构造方法,传入一个字节输出流对象
writeObject(Object obj)将一个对象信息写入文件中

对象的反序列化通过对象输入流来实现(ObjectInputStream)

ObjectInputStream常用方法方法阐述
ObjectInputStream(InputStream in)构造方法,传入一个字节输入流对象
Object readObject(Object obj)从文件中读一个对象信息,并返回该对象

由Object readObject(Object obj)看出,字节输入流也是创建对象的一种方式

import java.io.Serializable;

/*
如果一个类需要被序列化到文件中,那么这个类就需要实现Serializable接口,实现后,会自动的为该类生成一个序列化编号
编号是类的唯一标识

但是自动生成的编号在类信息改变后,会重新为类生成一个编号

可以在类中显示的生成一个编号,这样类信息修改后,也不会改变
 */

public class Student implements Serializable {

    private static final long serialVersionUID = 771652260758459933L; //类的序列化编号
    private int num;

    private String name;

    @Override
    public String toString() {
        return "Student{" +
                "num=" + num +
                ", name='" + name + '\'' +
                '}';
    }

    public Student(int num, String name) {
        this.num = num;
        this.name = name;
    }

    public int getNum() {
        return num;
    }

    public void setNum(int num) {
        this.num = num;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
}
public static void main(String[] args) throws IOException, ClassNotFoundException {

        //当一个类的对象需要被序列化到文件时,这个类必须要生成一个序列化编号
        Student student = new Student(100,"jim");

        //对象序列化
        FileOutputStream fileOutputStream = new FileOutputStream("E:/demo.txt");
        ObjectOutputStream outputStream = new ObjectOutputStream(fileOutputStream);
        outputStream.writeObject(student);
        outputStream.close();

        //对象的反序列化
        FileInputStream fileInputStream = new FileInputStream("E:/demo.txt");
        ObjectInputStream inputStream = new ObjectInputStream(fileInputStream);
        Student stu = (Student)inputStream.readObject();
        System.out.println(stu);
        inputStream.close();
    }
}

 

自定义一个学生类,要想通过对象输入输出流对自定义的类进行序列化和反序列化,就必须实现Serializable接口,实现这个接口的类默认会生成一个序列化编号,这个编号就相当于一个身份证号一样,若类发生改变会重新生成一个序列化编号,当我们从文件中读取对象信息时,就是通过这个序列化编号去寻找是哪一个类的对象.

正因为类发生变化,序列化编号也会跟着变化,那么如果我们需要修改类信息时,下一次就无法完成反序列化, 因为编译器会拿着这次修改的编号去文件中找,但是文件中还存储的是上一次序列化时产生的编号,显然两次编号不同,编译器会认为这不是同一个类,即不是我们要反序列化的类,就会报错

解决方法:

显示生成序列化编号,这样对于这个类来说,无论怎么修改,它的序列化编号都不发生改变,但切记修改类信息后需要重新序列化对象,否则反序列化的扔是上次未修改的对象

3. IDEA设置序列化编号提示

 

注意这是新版IDEA的操作,设置好后点击OK即可,这样在自定义的类中如果实现了Serializable接口,鼠标放到类名上就会显示

 

此时编译器就会自动生成一个序列化编号,这样无论怎么修改类信息,在对象进行序列化和反序列化时都不会报错,唯一需要注意的是,如果修改了类的信息,需要自己重新将对象序列化一次,才是修改后的对象信息,否则还是保存的上一次未修改的对象的信息

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1906171.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

实验代码结构介绍

提高模型复用性,让模型对应的配置更加清晰,代码书写条理 学习自https://zhuanlan.zhihu.com/p/409662511 Project ├── checkpoints # 存放模型 ├── data # 定义各种用于训练测试的数据集 ├── eval.py # 测试代码 ├── loss.py # 定义的…

CSS 后代选择器正确写法 爸爸儿子之间有代沟

CSS 后代选择器正确写法 爸爸儿子之间有代沟 example&#xff1a; > <body> > <div class"outer"> > <span class"inner"></span> > </div> > </body> > <head> > <style>…

如何选择快手矩阵源码:关键因素解析

在短视频行业迅速发展的今天&#xff0c;快手平台已成为众多内容创作者和企业的重要阵地。为了有效管理和运营多个快手账号&#xff0c;快手矩阵源码成为了一个关键工具。然而&#xff0c;市场上的快手矩阵源码种类繁多&#xff0c;选择一个合适的源码并非易事。本文将探讨选择…

【QT】多元素控件

多元素控件 多元素控件1. List Widget2. Table Widget3. Tree Widget 多元素控件 Qt 中提供的多元素控件有: QListWidgetQListViewQTableWidgetQTableViewQTreeWidgetQTreeView xxWidget 和 xxView 之间的区别&#xff0c;以 QTableWidget 和 QTableView 为例&#xff1a; …

WPS提示打印机异常,但是任然可以打印

故障现象 使用WPS在打印预览页时&#xff0c;打印机有小橙点提示&#xff0c;点击打印时会报错&#xff0c;提示&#xff1a; 打印机异常&#xff0c;打印机状态出现异常&#xff0c;请检查打印机是否开机并且联机 但是点击确定后&#xff0c;可以继续打印&#xff0c;而且其他…

企业微信hook接口协议,聊天标签中的联系人变动通知

聊天标签中的联系人变动通知 返回示例 {"send_time":1699256104,"flag":0,"receiver":0,"sender":10014,"referid":0,"sender_name":"","app_info":"0FUGGXUfQ0G7nPh","rea…

收藏!2024年程序员的实用神器_new relic idea

前言 Chat GPT的升级节奏让人们越来越惊讶的同时&#xff0c;也让大家感觉到了压力&#xff0c;在如此快节奏的互联网世界中&#xff0c;开发人员需要不断学习与更新知识&#xff0c;保持领先地位并高效地交付高质量软件。 无论是集成开发环境 (IDE)、版本控制系统、测试工具…

“除了C盘都不见了“:现象解析、恢复策略与预防之道

现象概述&#xff1a;非系统盘突然消失之谜 在日常的计算机使用中&#xff0c;不少用户可能遭遇过一个令人措手不及的问题——“除了C盘都不见了”。这一现象发生时&#xff0c;用户惊讶地发现除了作为系统盘的C盘外&#xff0c;原本存放着各类文档、图片、视频等个人资料的D盘…

得帆荣获中国信通院低代码标准参编专家认证和低代码白皮书参编单位认可

2024年6月26日&#xff0c;由中国通信标准化协会主办&#xff0c;中国通信标准化协会云计算标准和开源推进委员会承办的2024低代码无代码产业大会在北京召开&#xff0c;大会以“智融低无码&#xff0c;模创新未来”为主题&#xff0c;发布领域研究成果&#xff0c;交流行业前沿…

使用dd命令简单测试磁盘I/O

本文所有测试使用的均是Oracle公有云OCI上的计算实例的启动盘。 第1轮测试使用的是默认的启动盘参数。第2轮测试使用的是自动调整的启动盘参数&#xff08;如下图&#xff09;&#xff0c;性能更高。 第1轮测试 顺序I/O 运行以下命令5次&#xff0c;dsync表示不使用cache&…

【MySQL05】【 undo 日志】

文章目录 一、前言二、undo 日志&#xff08;回滚日志&#xff09;1. 事务 id2. undo 日志格式2.1 INSERT 对应的 undo 日志2.2 DELETE 对应的 undo 日志2.3 UPDATE 对应的 undo 日志2.3.1 不更新主键2.3.2 更新主键 2.3 增删改操作对二级索引的影响2.4 roll_pointer 3. FIL_PA…

合合信息大模型“加速器”重磅上线

大模型技术的发展和应用&#xff0c;预示着更加智能化、个性化未来的到来。如果将大模型比喻为正在疾驰的科技列车&#xff0c;语料便是珍贵的“燃料”。本次世界人工智能大会期间&#xff0c;合合信息为大模型打造的“加速器”解决方案备受关注。 在大模型训练的上游阶段&…

FPGA问题

fpga 问题 第一道坎&#xff0c;安装软件&#xff1b;没有注册&#xff0c;无法产生sop文件&#xff0c;无法下载 没有相应的库的quartus ii版本&#xff0c;需要另下载 第二道坎&#xff0c;模拟器的下载&#xff0c;安装&#xff1b; 第三道&#xff0c;verilog 语法&#x…

PLM设计协同、PLM在产品开发初期的优化作用

在当今快速变化的市场环境中&#xff0c;产品的成功不再仅仅依赖于其最终的功能与性能&#xff0c;更在于其从概念到市场的整个生命周期的效率和效果。产品生命周期管理&#xff08;Product Lifecycle Management, PLM&#xff09;作为一种集成了数据、流程和工具的综合方法&am…

破局 AI 2.0 时代:利用 AI 提升自我核心竞争力

文章目录 破局 AI 2.0 时代&#xff1a;利用 AI 提升自我核心竞争力1. AI 2.0 时代1.1 特点1.2 发展1.3 影响 2. AI 2.0 时代的机遇 & 挑战2.1 AI 对行业市场的冲击2.2 挑战变为机遇2.3 不同场景下的 AI 效能提升2.3.1 自动化办公任务2.3.2 提升学习效率2.3.3 创意生成与内…

微信小程序的餐厅点餐系统-计算机毕业设计源码71834

摘要 随着移动互联网技术的迅猛发展&#xff0c;微信小程序因其便捷性和即用即走的特性&#xff0c;成为了连接用户与服务的新桥梁。Node.js作为一种高效、轻量级的后端技术&#xff0c;为开发者提供了快速构建服务器端应用的能力。本文介绍了一个基于微信小程序和Node.js的餐厅…

【小贪】程序员必备:Shell、Git、Vim常用命令

近期致力于总结科研或者工作中用到的主要技术栈&#xff0c;从技术原理到常用语法&#xff0c;这次查缺补漏当作我的小百科。主要技术包括&#xff1a; ✅数据库常用&#xff1a;MySQL, Hive SQL, Spark SQL✅大数据处理常用&#xff1a;Pyspark, Pandas⚪ 图像处理常用&#…

【嵌入式单片机】之RS-232、RS-485、RS-422比较

1. RS422是什么 RS422,正式名称为TIA/EIA-422,是一种串行通信标准,专为实现长距离、高可靠性的数据传输而设计。它采用差分信号传输技术,通过两对双绞线实现全双工通信,即发送和接收可以同时进行。RS422在工业自动化和远程监控系统中曾经扮演着重要角色,以其出色的抗干扰…

新衣服不香了!欧洲人越来越喜欢二手时尚品,国外有哪些二手交易平台?

在欧美国家&#xff0c;大家都很热衷于购买二手商品。过去网店不太盛行的时候&#xff0c;买衣服最喜欢逛二手店。现如今&#xff0c;随着经济和环保观念的普及&#xff0c;也有了二手交易平台&#xff0c;大家的热情也从线下转到了线上。 新衣服不香了&#xff01;欧洲人越来越…

深入分析 Android BroadcastReceiver (十)(完)

文章目录 深入分析 Android BroadcastReceiver (十)1. 深入理解 Android 广播机制的高级应用与实践1.1 高级应用1.1.1 示例&#xff1a;广播启动服务1.1.2 示例&#xff1a;数据变化通知1.1.3 示例&#xff1a;下载完成通知 1.2 实践建议1.2.1 设置权限1.2.2 动态注册和注销广播…