Java进阶——IO流(II)
创始人
2024-03-27 01:23:45
0

文章目录

    • 三、节点流和处理流
      • 3.1、处理流BufferedReader和BufferedWriter
      • 3.2、处理流BufferedInputStream和BufferedOutputStream
      • 3.3、对象流ObjectInputStream和ObjectOutputStream
      • 3.4、标准输入输出流
      • 3.5、转换流InputStreamReader和OutputStreamWriter
      • 3.6、打印流**PrintStream** 和 PrintWriter
    • 四、Properties类

三、节点流和处理流

基本介绍:

image-20221114151045919

  • 节点流和处理流

image-20221114151238588

3.1、处理流BufferedReader和BufferedWriter

  • BufferedReader和BufferedWriter属于字符流,是按照字符来读取数据的关闭时,只需要关闭外层

BufferedReader代码演示:

import org.junit.jupiter.api.Test;import java.io.BufferedReader;
import java.io.FileNotFoundException;
import java.io.FileReader;/*** @author java小豪* @version 1.0.0* @date 2022/11/16* @description 处理流*/
public class BufferedReader_ {public static void main(String[] args) {}@Testpublic void read() throws Exception {String filePath = "F:\\file\\story.txt";// 创建BufferedReader对象BufferedReader bufferedReader = new BufferedReader(new FileReader(filePath));// 读取String line;// 说明// 1.bufferedReader.readLine() 是按行读取文件// 2.当返回null 时,表示文件读取完毕while ((line = bufferedReader.readLine()) != null) {System.out.print(line);}// 关闭流 只需要关闭 BufferedReader, 因为底层会自动关闭 节点流bufferedReader.close();}
}

**BufferedWriter代码演示:**不能处理二进制文件[pdf/word/声音/图片等]

import org.junit.jupiter.api.Test;import java.io.*;/*** @author java小豪* @version 1.0.0* @date 2022/11/16* @description 文件拷贝*/
public class BufferedCopy_ {public static void main(String[] args) {}@Testpublic void test() {String filePath = "F:\\file\\ok.txt";String destFilePath = "F:\\file\\ok1.txt";BufferedReader bufferedReader = null;BufferedWriter bufferedWriter = null;String line;try {bufferedReader = new BufferedReader(new FileReader(filePath));bufferedWriter = new BufferedWriter(new FileWriter(destFilePath));// readLine() 读取一行内容,但是没有换行while ((line = bufferedReader.readLine()) != null) {// 每读取一行就写进去bufferedWriter.write(line);// 插入一个换行bufferedWriter.newLine();}System.out.println("拷贝完毕....");} catch (IOException e) {e.printStackTrace();} finally {try {if (bufferedReader != null) {// 关闭流bufferedReader.close();}if (bufferedWriter != null) {// 关闭流bufferedWriter.close();}} catch (IOException e) {e.printStackTrace();}}}}

3.2、处理流BufferedInputStream和BufferedOutputStream

  • 使用BufferedInputStream和BufferedOutputStream可以完成二进制文件的拷贝
import org.junit.jupiter.api.Test;import java.io.*;/*** @author java小豪* @version 1.0.0* @date 2022/11/16* @description 文件拷贝*/
public class BufferedCopy1 {public static void main(String[] args) {}@Testpublic void copy() {String srcPath = "F:\\file\\1.jpg";String destPath = "F:\\file\\2.jpg";// 创建BufferedInputStream和BufferedOutputStreamBufferedInputStream bis = null;BufferedOutputStream bos = null;try {bis = new BufferedInputStream(new FileInputStream(srcPath));bos = new BufferedOutputStream(new FileOutputStream(destPath));// 循环读取文件,并写入到 destPathbyte[] bytes = new byte[1024];int readLine = 0;// 当返回 -1 时表示读取完毕while((readLine = bis.read(bytes)) != -1) {bos.write(bytes, 0, readLine);}System.out.println("文件拷贝完毕....");} catch (IOException e) {e.printStackTrace();} finally {// 关闭流,关闭外层的处理流try {if (bis != null) {bis.close();}if (bos != null) {bos.close();}} catch (IOException e) {e.printStackTrace();}}}
}

3.3、对象流ObjectInputStream和ObjectOutputStream

  • 序列化和反序列化
  1. 序列化就是在保存数据时,保存数据的值数据类型
  2. 反序列化就是在恢复数据时,恢复数据的值数据类型
  3. 需要让某个对象支持序列化,必须让其类是可序列化的,必须实现如下两个接口之一:Serializable(标记接口)和Externalizable

ObjectInputStream和ObjectOutputStream的类图:


image-20221116140250301

image-20221116140231862

使用ObjectOutputStream 序列化基本数据类行和一个Dog对象(name, age)并保存到data.dat文件里面

import java.io.*;/*** @author java小豪* @version 1.0.0* @date 2022/11/16* @description ObjectOutputStream的使用*/
public class ObjectOutputStream_ {public static void main(String[] args) throws IOException {// 序列化后保存的文件格式,不是纯文本,而是按照它的格式保存的String filePath = "F:\\file\\data.dat";ObjectOutputStream os = new ObjectOutputStream(new FileOutputStream(filePath));// 序列化数据os.write(100);// 自动装箱boolean ----> Boolean (实现了 Serializable)os.writeBoolean(true);// 自动装箱char ----> Character (实现了 Serializable)os.writeChar('a');os.writeUTF("java小豪");// 保存一个Dog对象os.writeObject(new Dog("旺财", 3));os.close();System.out.println("数据保存完毕(序列化形式)");}
}
// 如果需要序列化某个类的对象,实现Serializable
class Dog implements Serializable {private String name;private int age;public Dog(String name, int age) {this.name = name;this.age = age;}
}
  • 注意事项
    • 读写顺序要一致
    • 要求实现序列化或反序列化对象实现Serializable
    • 序列化对象时,默认将里面的所有属性都进行序列化,除了static或transient修饰的成员
    • 序列化对象时,要求里面的属性的类型也需要实现序列化接口
    • 序列化具备可继承性,也就是某类实现了序列化,他的所有子类也已经默认实现了序列化

3.4、标准输入输出流

  • System.in和System.out
/*** @author java小豪* @version 1.0.0* @date 2022/11/16* @description 标准输入和输出流*/
public class InputAndOutput {public static void main(String[] args) {//System类里面的一个属性 public final static InputStream in = null;// 编译类型 为 InputStream 运行类型 BufferedInputStreamSystem.out.println(System.in.getClass());// System.out 是 public final static PrintStream out = null;// 编译类型 为 PrintStream 运行类型 为PrintStream 标准输出(显示器)System.out.println(System.out.getClass());}
}

3.5、转换流InputStreamReader和OutputStreamWriter

  1. InputStreamReader: Reader的子类,可以将InputStream(字节流)包装成(转换)Reader(字符流)
  2. OutputStreamWriter: Writer的子类,可以实现将OutputStream(字节流)包装成Writer(字符流)
  3. 当处理纯文本数据时,如果使用字符流效率更高,并且可以有效解决中文问题,所以建议将字节流转换成字符流
  4. 可以在使用时指定编码格式(比如 utf-8, gbk, gb2312, ISO8855-1等)

InputStreamReader的类图:

image-20221128215734373


OutputStream的类图:

image-20221128220657123


**示例1:**字节流FileInputStream包装成(转换成)字符流InputStreamReader,对文件进行读取(按照UTF-8/GBK格式)进而包装成BufferedReader

import java.io.*;/*** @author java小豪* @version 1.0.0* @date 2022/11/28* @description 使用InputStreamReader解决中文乱码问题* 

* 将字节流 FileInputStream 转换成 InputStreamReader, 指定编码gbk/utf-8*

*/ public class InputStreamReader_ {public static void main(String[] args) throws IOException {String filePath = "F:\\file\\a.txt";// 1. new FileInputStream 转成 InputStreamReader 指定编码为GBKInputStreamReader isr = new InputStreamReader(new FileInputStream(filePath), "GBK");// 2. 把 InputStreamReader 传入 BufferedReaderBufferedReader br = new BufferedReader(isr);// 将 2 和 3 和在一起// BufferedReader br = new BufferedReader(new InputStreamReader(new FileInputStream(filePath), "GBK"));// 3. 读取String s = br.readLine();System.out.println("读取文件的内容为:" + s);// 4. 关闭外层流br.close();} }

**示例2:**将字节流FileOutputStream包装成(转换成)字符流OutputStreamWriter,对文件进行写入(按照GBK格式,可以指定其他:UTF-8)

import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStreamWriter;/*** @author java小豪* @version 1.0.0* @date 2022/11/28* @description 使用OutputStreamWriter将FileOutputStream字节流,转换成字符流 OutputStreamWriter*/
public class OutputStreamWriter_ {public static void main(String[] args) throws IOException {String filePath = "F:\\file\\a.txt";String charSet = "UTF-8";OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream(filePath), charSet);osw.write("hi, 孙悟空");osw.close();System.out.println("按照 " + charSet + "保存文件成功~");}
}

3.6、打印流PrintStream 和 PrintWriter

注意:打印流只有输出流,没有输入流
PrintStream的类图

image-20221128223541729

PrintWriter的类图

image-20221128223641038

PrintStream示例:

import java.io.IOException;
import java.io.PrintStream;/*** @author java小豪* @version 1.0.0* @date 2022/11/28* @description 演示PrintStream(字节打印流)、*/
public class PrintStream_ {public static void main(String[] args) throws IOException {PrintStream ps = System.out;// 默认情况下,PrintStream 输出数据的位置是标准输出/*public void print(String s) {if (s == null) {s = "null";}write(s);}*/ps.println("john Hello");// 因为print底层使用write,所以我们可以调用write进行打印/输出ps.write("孙悟空,你好".getBytes());ps.close();//我们可以修改打印输出流的位置,修改成到 "F:\\file\\f1.txt"System.setOut(new PrintStream("F:\\file\\f1.txt"));System.out.println("hello, 孙悟空");}
}

PrintWriter示例:

import java.io.FileWriter;
import java.io.IOException;
import java.io.PrintWriter;/*** @author java小豪* @version 1.0.0* @date 2022/11/28* @description 演示PrintWriter的使用*/
public class PrintWriter_ {public static void main(String[] args) throws IOException {//        PrintWriter pw = new PrintWriter(System.out);PrintWriter pw = new PrintWriter(new FileWriter("F:\\file\\f2.txt"));pw.print("hello, 北京~");pw.close();}
}

四、Properties类

properties类可以轻松的处理*.properties文件

Properties类常见方法:

  • load:加载配置文件的键值对到Properties对象
  • list:将数据显示到指定位置
  • getProperty(key):根据键获取值
  • setProperty(key, value):设置键值对到Properties对象
  • store:将Properties中的键值对存储到配置文件,在idea中保存文件如果有中文,会存储为Unicode码

**示例1:**读取mysql.properties文件,并得到ip,user 和 pwd

  • 传统方法
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;/*** @author java小豪* @version 1.0.0* @date 2022/11/28* @description 演示Properties类的使用*/
public class Properties01 {public static void main(String[] args) throws IOException {// 读取mysql.properties文件并得到ip、user和pwdBufferedReader br = new BufferedReader(new FileReader("src\\mysql.properties"));String line = "";while((line = br.readLine()) != null ) {String[] split = line.split("=");System.out.println(split[0] + "值是:" + split[1]);}br.close();}
}
  • 使用Properties类进行读取
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.util.Properties;/*** @author java小豪* @version 1.0.0* @date 2022/11/28* @description*/
public class Properties02 {public static void main(String[] args) throws IOException {// 使用Properties 类来读取mysql.properties 文件// 1.创建Properties 对象Properties properties = new Properties();// 2.加载指定的配置文件properties.load(new FileReader("src/mysql.properties"));// 3.把k-v显示到控制台properties.list(System.out);// 4.根据键获取对应的值String user = properties.getProperty("username");String pwd = properties.getProperty("password");System.out.println("用户名=" + user);System.out.println("密码=" + pwd);}
}
  • 使用Properties修改配置文件
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Properties;/*** @author java小豪* @version 1.0.0* @date 2022/11/29* @description*/
public class Properties03 {public static void main(String[] args) throws IOException {// 使用Properties 类来创建 配置文件,修改配置文件内容Properties properties = new Properties();// 创建// 1.如果该文件没有key,就是创建// 2.如果该文件有key,就是修改properties.setProperty("charset", "utf-8");properties.setProperty("user", "孙悟空");properties.setProperty("pwd", "888888");// 将k-v 存储在文件中properties.store(new FileOutputStream("src\\mysql2.properties"), null);System.out.println("保存文件成功");}
}

相关内容

热门资讯

AWSECS:访问外部网络时出... 如果您在AWS ECS中部署了应用程序,并且该应用程序需要访问外部网络,但是无法正常访问,可能是因为...
银河麒麟V10SP1高级服务器... 银河麒麟高级服务器操作系统简介: 银河麒麟高级服务器操作系统V10是针对企业级关键业务...
【NI Multisim 14...   目录 序言 一、工具栏 🍊1.“标准”工具栏 🍊 2.视图工具...
不能访问光猫的的管理页面 光猫是现代家庭宽带网络的重要组成部分,它可以提供高速稳定的网络连接。但是,有时候我们会遇到不能访问光...
AWSElasticBeans... 在Dockerfile中手动配置nginx反向代理。例如,在Dockerfile中添加以下代码:FR...
Android|无法访问或保存... 这个问题可能是由于权限设置不正确导致的。您需要在应用程序清单文件中添加以下代码来请求适当的权限:此外...
月入8000+的steam搬砖... 大家好,我是阿阳 今天要给大家介绍的是 steam 游戏搬砖项目,目前...
​ToDesk 远程工具安装及... 目录 前言 ToDesk 优势 ToDesk 下载安装 ToDesk 功能展示 文件传输 设备链接 ...
北信源内网安全管理卸载 北信源内网安全管理是一款网络安全管理软件,主要用于保护内网安全。在日常使用过程中,卸载该软件是一种常...
AWS管理控制台菜单和权限 要在AWS管理控制台中创建菜单和权限,您可以使用AWS Identity and Access Ma...