Java学习【IO流:深入理解与应用(上)】
Java学习【IO流:深入理解与应用(上)】
- 🍃1.IO流体系结构
- 🍃2.FileOutputStream
- 🍁2.1FileOutputStream写数据的三种方式
- 🍁2.2换行和续写
- 🍃3.FileInputStream
- 🍁3.1每次读取一个字节
- 🍁3.2读取多个字节
- 🍃文件拷贝
- 🍃IO流中的异常处理方式
🚀所属专栏:Java学习⭐⭐
🚀欢迎互三👉: 2的n次方_⭐⭐
🍃1.IO流体系结构
在Java编程中,IO(Input/Output)流是一个非常重要的概念,它允许我们与各种数据源(如文件、网络、内存等)进行交互。Java的IO库提供了丰富的类和方法,用于读取和写入数据。
IO流按照操作文件类型又可以分为
字节流:可以操作所有类型文件
字符流:只能操作纯文本文件
由于上面的四个都是抽象类,在实现的时候要创建子类的对象,这里以字节流为例,下面是其两个子类
🍃2.FileOutputStream
FileOutputStream:操作本地文件的字节输出流,可以把程序中的数据写入到本地文件中。
1.参数是字符串表示的路径或者File对象都可以
2.如果文件不存在就会创建一个新的文件,但是要保证父级路径是存在的
3.如果文件存在,那么会清空文件中的数据,然后再写入
写入文件时,传入参数是整数,会转换为ASCII码对应的字符
如果想要写入整型,就分开写对应的ASCII码
🍁2.1FileOutputStream写数据的三种方式
创建对象之后是通过调用write()方法进行写入
FileOutputStream fos = new FileOutputStream("E:\\java\\a.txt");// 写入一个数据fos.write(97);
这里会出现异常,将异常进行抛出处理
write()也提供了其他的重载方法
可以传入一个byte类型的数组,写入多个字节,还可以指定写入的起始索引,再指出写入几个字节
byte[] bytes = {97, 98, 99, 100};fos.write(bytes);//从1索引开始写入两个字符fos.write(bytes, 1, 2);
每次执行操作结束之后都要调用close()方法进行资源释放,否则文件就会一直被占用
public class ByteStreamDemo1 {public static void main(String[] args) throws IOException {FileOutputStream fos = new FileOutputStream("E:\\java\\a.txt");// 写入一个数据fos.write(97);//写入多个数据byte[] bytes = {97, 98, 99, 100};fos.write(bytes);//从1索引开始写入两个字符fos.write(bytes, 1, 2);//释放资源,解除资源占用fos.close();}
}
🍁2.2换行和续写
除了以上三种写入方式外,还可以通过字符串的方式进行写入
此外,如果需要写入换行,在windows操作系统中,是用 “\r\n” 表示换行
public class ByteStreamDemo1 {public static void main(String[] args) throws IOException {FileOutputStream fos = new FileOutputStream("E:\\java\\a.txt");//写入字符串String str = "hello";byte[] bytes1 = str.getBytes();fos.write(bytes1);//写入换行String s = "\r\n";fos.write(s.getBytes());fos.write(97);//释放资源,解除资源占用fos.close();}
}
打开记事本查看a.txt的内容
续写就是不清空原来文件的内容,接着往下写
FileOutputStream()的构造方法还有一个boolean类型的参数,表示续写开关,默认是false,如果创建对象时给出true,那么就表示续写,此时就不会清空原来文件的内容
public class ByteStreamDemo1 {public static void main(String[] args) throws IOException {//续写,之前内容不会清空FileOutputStream fos1 = new FileOutputStream("E:\\java\\a.txt", true);//打开续写fos1.write("666".getBytes());//释放资源fos1.close();}
}
可以看出,这次是接着上次的内容继续进行写入的
🍃3.FileInputStream
操作本地文件的字节输入流,可以把本地文件中的数据读取到程序中来
🍁3.1每次读取一个字节
第一步也是创建对象,接着调用read()方法,就可以读取到一个字节的内容,读到的内容也是ASCII码对应的数字
public class ByteStreamDemo2 {public static void main(String[] args) throws IOException {//字节输出入流,如果文件不存在,就会报错FileInputStream fis = new FileInputStream("E:\\java\\a.txt");//读取一个字节,读取到末尾再继续读会返回-1int res = fis.read();System.out.println((char) res);//释放资源fis.close();}
}
创建对象时,如果对应路径不存在,就会直接报错,此外,读取到末尾之后继续读就会返回-1,那么文件中最后确实是-1的话怎么判断呢?“-1"其实是分为”-" 和 "1"的,所以并不冲突
根据这个特性可以进行文件的循环读取
int a = 0;while ((a = fis.read() )!= -1){System.out.print((char)a);}System.out.println();
问题:如果不用一个变量来接收行不行?
while(fis.read() != -1){System.out.println((char)fis.read());}
答:因为每次调用read就表示往后移动一位,所以每次循环都进行了两次读取(判断条件一次,输出语句一次),打印的数据其实是跳跃的
🍁3.2读取多个字节
如果要读取多个字节,可以在read方法中传入一个byte类型的数组,数组长度是多少每次就读几个字节
public class ByteStreamDemo2 {public static void main(String[] args) throws IOException {//字节输出入流,如果文件不存在,就会报错FileInputStream fis = new FileInputStream("E:\\java\\a.txt");//读取多个字节byte[] byte1 = new byte[3];int len1 = fis.read(byte1);System.out.println(new String(byte1));System.out.println(len1);//如果继续往下读,因为文件中剩余的数据不足数组的长度,只覆盖读取到了的数据int len2 = fis.read(byte1);System.out.println(new String(byte1));System.out.println(new String(byte1,0,len2));//只打印读到的数据System.out.println(len2);//释放资源fis.close();}
}
如果继续往下读,文件中剩余的数据不足数组的长度,只覆盖读取到的数据,此时就可以把读取的字节数进行一个返回,只打印读取到的数据,也就是没有被覆盖的数据不打印
🍃文件拷贝
文件拷贝就是把读取和写入结合起来,把读取到的数据再写入另一个文件中,所以也有两种方式进行拷贝,一种是一个字节一个字节的拷贝,另一种就是直接定义一个大容量的数组,一次拷贝完成,很显然,后者更加高效
public class ByteStreamDemo3 {public static void main(String[] args) throws IOException {FileInputStream fis = new FileInputStream("E:\\java\\a.txt");FileOutputStream fos = new FileOutputStream("E:\\java\\b.txt");//一次拷贝一个字节int b1 = 0;while ((b1 = fis.read()) != -1) {fos.write(b1);}//一次拷贝多个字节byte[] b2 = new byte[1024];int len = 0;while((len = fis.read(b2)) != -1){fos.write(b2,0,len);}//释放资源,先开后关fos.close();fis.close();}
}
最后释放资源的时候需要注意,遵循最先打开的文件最后关闭的原则
🍃IO流中的异常处理方式
在之前,我们都是对异常进行抛出处理,怎么去使用try - catch处理呢?
首先需要明白,程序最后都要进行资源释放,所以就可以采用try - catch - finally结构,把资源释放的模块放在finally里
如果按照正常的想法,把有异常的模块都放进try里,此时创建出的对象就属于局部变量,finally里调用不了,就需要把创建对象的部分写在外面
但此时还是报错了,还需要对finally的内容进行异常处理
这样看貌似是没有问题了,但是还是有一个细节需要注意,如果创建对象时给的路径不存在,还是会报错,除了正常给出的路径异常,还有一个空指针异常
就需要处理对象为空的情况
public class ByteStreamDemo4 {public static void main(String[] args) {FileInputStream fis = null;FileOutputStream fos = null;try {fis = new FileInputStream("E:\\java\\a.txt");fos = new FileOutputStream("E:\\java\\b.txt");//一次拷贝多个字节byte[] b = new byte[1024];int len = 0;while ((len = fis.read(b)) != -1) {fos.write(b, 0, len);}} catch (IOException e) {e.printStackTrace();} finally {//释放资源,先开后关if (fos != null) {try {fos.close();} catch (IOException e) {e.printStackTrace();}}if (fis != null) {try {fis.close();} catch (IOException e) {e.printStackTrace();}}}}
}
此时再运行就没有空指针异常了
上面的代码看起来很多,在JDK7和JDK9种给出了两种简化版本,推出了AutoCloseable接口,它定义了一个可以被自动关闭的资源,确保在 try 代码块执行完毕后,资源能够自动关闭,即使发生了异常,但是只能在特定的情况可以使用
JDK7:
JDK9:
这样就不用在finally种写一堆对释放资源处理的异常了,不过,一般情况下直接抛出就可以了
相关文章:

Java学习【IO流:深入理解与应用(上)】
Java学习【IO流:深入理解与应用(上)】 🍃1.IO流体系结构🍃2.FileOutputStream🍁2.1FileOutputStream写数据的三种方式🍁2.2换行和续写 🍃3.FileInputStream🍁3.1每次读取…...
干货系列:SpringBoot3第三方接口调用10种方式
环境:SpringBoot.3.3.0 1、简介 在项目中调用第三方接口是日常开发中非常常见的。调用方式的选择通常遵循公司既定的技术栈和架构规范,以确保项目的一致性和可维护性。无论是RESTful API调用、Feign声明式HTTP客户端、Apache HttpClient等调用方式&…...

KVM性能优化之CPU优化
1、查看kvm虚拟机vCPU的QEMU线程 ps -eLo ruser,pid,ppid,lwp,psr,args |awk /^qemu/{print $1,$2,$3,$4,$5,$6,$8} 注:vcpu是不同的线程,而不同的线程是跑在不同的cpu上,一般情况,虚拟机在运行时自身会点用3个cpus,为保证生产环…...

lua中判断2个表是否相等
当我们获取 table 长度的时候无论是使用 # 还是 table.getn 其都会在索引中断的地方停止计数,而导致无法正确取得 table 的长度,而且还会出现奇怪的现象。例如:t里面有3个元素,但是因为最后一个下表是5和4,却表现出不一…...

uni-app 自定义支付密码键盘
1.新建组件 payKeyboard .vue <template><view class"page-total" v-show"isShow"><view class"key-list"><view class"list" v-for"(item,index) in keyList" :class"{special:item.keyCode190…...

抖音微短剧小程序源码搭建:实现巨量广告数据高效回传
在数字化营销日益盛行的今天,抖音微短剧小程序已成为品牌与观众互动的新渠道。这些短小精悍的剧目不仅能迅速抓住用户的注意力,还能有效提升品牌的知名度和用户黏性。然而,想要充分利用这一营销工具,关键在于如何高效地追踪广告数…...

springboot数字化医院产科系统源码
目录 一、系统概述 二、开发环境 三、功能设计 四、功能介绍 一、系统概述 数字化产科是为医院产科量身定制的信息管理系统。它管理了孕妇从怀孕开始到生产结束42天一系列医院保健服务信息。该系统由门诊系统、住院系统、数据统计模块三部分组成,与医院HIS、LI…...

uniapp微信接口回调 response.sendRedirect nginx 报404错误
如题 参考 uniapp打包H5时,访问index.html页面白屏报错net::ERR_ABORTED 404 - 简书 nginx中修改 配置文件 location / { try_files $uri $uri/ /index.html; root html; index index.html index.htm; } uniapp里配置 重新载入...

Python系统教程02
巩固 input()输出函数 回顾 1 、 input()函数: 在 input()函数输入时,输入的内容一定为字符串类型。 2 、条件分支语句: 每一个 if 语句可以看成一个个体,elif 和 else 都是一个 if 个体的一部分,每一个 if 个体 运…...
JS面试题6——深拷贝和浅拷贝
它们都是用来复制的 1. 浅拷贝(只复制引用,而未复制真正的值) /* 简单赋值 */ var arr1 [a, b, c, d]; var arr2 arr1; /* Object.assign实现的也是浅拷贝 */ var obj1 {a:1, b:2} var obj2 Object.assign(obj1); 2. 深拷贝(是…...
Scrapy实现关键词搜索的数据爬取
爬虫技术对于从互联网上获取数据和信息非常重要,而scrapy作为一款高效、灵活和可扩展的网络爬虫框架,能够简化数据爬取的过程,对于从互联网上爬取数据的工作非常实用。本文将介绍如何使用scrapy实现关键词搜索的数据爬取。 Scrapy的介绍 Sc…...
【Linux】ip命令详解
Linux中的ip命令是一个功能强大的网络配置工具,用于显示或操作路由、网络设备、策略路由和隧道。以下是关于ip命令的详细解释: 一、ip命令介绍 简介:ip命令是一个用于显示或操作路由、网络设备、策略路由和隧道的Linux命令行工具。它取代了早期的ifconfig命令,并提供了更多…...

软降工程学系统实现
一、程序编码 程序编码是设计的继续,将软件设计的结果翻译成用某种程序设计语言描述的源代码。 程序编码涉及到方法、工具和过程。 程序设计风格和程序设计语言的特性会深刻地影响软件的质量和可维护性。 要求源程序具有良好的结构性和设计风格。 程序设计风格…...

001 SpringMVC介绍
文章目录 基础概念介绍BS和CS开发架构应用系统三层架构MVC设计模式 SpringMVC介绍SpringMVC是什么SpringMVC与Spring的联系为什么要学习SpringMVC 六大组件介绍六大组件(MVC组件其他三大组件)说明 基础概念介绍 BS和CS开发架构 一种是C/S架构,也就是客户端/服务器…...
深入解析scikit-learn中的交叉验证方法
交叉验证是机器学习中用于评估模型性能的重要技术,它可以帮助我们理解模型在未知数据上的泛化能力。scikit-learn(简称sklearn)是一个广泛使用的Python机器学习库,提供了多种交叉验证方法。本文将详细介绍scikit-learn中提供的交叉…...

分布式kettle调度管理平台简介
介绍 Kettle(也称为Pentaho Data Integration)是一款开源的ETL(Extract, Transform, Load)工具,由Pentaho(现为Hitachi Vantara)开发和维护。它提供了一套强大的数据集成和转换功能,…...

002-基于Sklearn的机器学习入门:基本概念
本节将继续介绍与机器学习有关的一些基本概念,包括机器学习的分类,性能指标等。同样,如果你对本节内容很熟悉,可直接跳过。 2.1 机器学习概述 2.1.1 什么是机器学习 常见的监督学习方法 2.1.2 机器学习的分类 机器学习一般包括监…...
ubuntu 默认的PATH配置
ubuntu 默认的PATH配置 在Ubuntu系统中,PATH环境变量是非常关键的,因为它定义了操作系统在接收到用户输入命令时,搜索可执行文件的目录顺序。这个变量的配置决定了哪些命令可以被系统全局识别和执行。 默认的PATH配置 Ubuntu的默认PATH环境…...

JAVA妇产科专科电子病历系统源码,前端框架:Vue,ElementUI
JAVA妇产科专科电子病历系统源码,前端框架:Vue,ElementUI孕产妇健康管理信息管理系统是一种将孕产妇健康管理信息进行集中管理和存储的系统。通过建立该系统,有助于提高孕产妇健康管理的效率和质量,减少医疗事故发生的…...
代码随想录算法训练营Day56|所有可达路径、797.所有可能的路径
所有可达路径 98. 所有可达路径 (kamacoder.com) 深度优先搜索,和之前的回溯题类似。 #include <iostream> #include <vector> using namespace std;// 定义一个二维向量来存储所有可能的路径 vector<vector<int>> paths; // 定义一个向…...

【力扣数据库知识手册笔记】索引
索引 索引的优缺点 优点1. 通过创建唯一性索引,可以保证数据库表中每一行数据的唯一性。2. 可以加快数据的检索速度(创建索引的主要原因)。3. 可以加速表和表之间的连接,实现数据的参考完整性。4. 可以在查询过程中,…...
【ROS】Nav2源码之nav2_behavior_tree-行为树节点列表
1、行为树节点分类 在 Nav2(Navigation2)的行为树框架中,行为树节点插件按照功能分为 Action(动作节点)、Condition(条件节点)、Control(控制节点) 和 Decorator(装饰节点) 四类。 1.1 动作节点 Action 执行具体的机器人操作或任务,直接与硬件、传感器或外部系统…...

DBAPI如何优雅的获取单条数据
API如何优雅的获取单条数据 案例一 对于查询类API,查询的是单条数据,比如根据主键ID查询用户信息,sql如下: select id, name, age from user where id #{id}API默认返回的数据格式是多条的,如下: {&qu…...

使用 SymPy 进行向量和矩阵的高级操作
在科学计算和工程领域,向量和矩阵操作是解决问题的核心技能之一。Python 的 SymPy 库提供了强大的符号计算功能,能够高效地处理向量和矩阵的各种操作。本文将深入探讨如何使用 SymPy 进行向量和矩阵的创建、合并以及维度拓展等操作,并通过具体…...
NPOI Excel用OLE对象的形式插入文件附件以及插入图片
static void Main(string[] args) {XlsWithObjData();Console.WriteLine("输出完成"); }static void XlsWithObjData() {// 创建工作簿和单元格,只有HSSFWorkbook,XSSFWorkbook不可以HSSFWorkbook workbook new HSSFWorkbook();HSSFSheet sheet (HSSFSheet)workboo…...
【Android】Android 开发 ADB 常用指令
查看当前连接的设备 adb devices 连接设备 adb connect 设备IP 断开已连接的设备 adb disconnect 设备IP 安装应用 adb install 安装包的路径 卸载应用 adb uninstall 应用包名 查看已安装的应用包名 adb shell pm list packages 查看已安装的第三方应用包名 adb shell pm list…...

uniapp 小程序 学习(一)
利用Hbuilder 创建项目 运行到内置浏览器看效果 下载微信小程序 安装到Hbuilder 下载地址 :开发者工具默认安装 设置服务端口号 在Hbuilder中设置微信小程序 配置 找到运行设置,将微信开发者工具放入到Hbuilder中, 打开后出现 如下 bug 解…...

AI语音助手的Python实现
引言 语音助手(如小爱同学、Siri)通过语音识别、自然语言处理(NLP)和语音合成技术,为用户提供直观、高效的交互体验。随着人工智能的普及,Python开发者可以利用开源库和AI模型,快速构建自定义语音助手。本文由浅入深,详细介绍如何使用Python开发AI语音助手,涵盖基础功…...

嵌入式学习之系统编程(九)OSI模型、TCP/IP模型、UDP协议网络相关编程(6.3)
目录 一、网络编程--OSI模型 二、网络编程--TCP/IP模型 三、网络接口 四、UDP网络相关编程及主要函数 编辑编辑 UDP的特征 socke函数 bind函数 recvfrom函数(接收函数) sendto函数(发送函数) 五、网络编程之 UDP 用…...
用递归算法解锁「子集」问题 —— LeetCode 78题解析
文章目录 一、题目介绍二、递归思路详解:从决策树开始理解三、解法一:二叉决策树 DFS四、解法二:组合式回溯写法(推荐)五、解法对比 递归算法是编程中一种非常强大且常见的思想,它能够优雅地解决很多复杂的…...