Java学习路线-27:IO操作深入与IO操作类继承体系

举报
彭世瑜 发表于 2021/08/14 01:30:45 2021/08/14
【摘要】 第17 章 : IO操作深入 80 字符编码 常用的编码 1、GBK/GB2312 国标编码, GB2312简体中文,GBK包含简体和繁体 2、ISO8859-1 国际通用编码,描述所有字母 3、UNICODE 16进制存储,描述所有问题 4、UTF 象形文字部分使用16进制,普通字母采用ISO8859-1,主要使用UTF-8 列出本机属性 System.get...

第17 章 : IO操作深入

80 字符编码

常用的编码
1、GBK/GB2312 国标编码, GB2312简体中文,GBK包含简体和繁体
2、ISO8859-1 国际通用编码,描述所有字母
3、UNICODE 16进制存储,描述所有问题
4、UTF 象形文字部分使用16进制,普通字母采用ISO8859-1,主要使用UTF-8

列出本机属性

System.getProperties().list(System.out);

  
 
  • 1

项目中出现乱码问题就是编码和解码标准不统一

81 内存操作流

文件操作流 以文件为操作终端,InputStream、OutputStream

内存操作流
1、字节内存操作流 ByteArrayOutputStream ByteArrayInputStream
2、字符内存操作流 CharArrayWriter CharArrayReader

继承关系

OutputStream -FileOutputStream -ByteArrayOutputStream

InputStream -FileInputStream -ByteArrayInputStream 

Writer -OutputStreamWriter -FileWriter -CharArrayWriter

Reader -InputStreamReader -FileReader -CharArrayReader


  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18

示例:利用内存流小写转大写操作

import java.io.*;

class Demo{ public static void main(String[] args) throws IOException { String message = "hello java"; // 将数据保存到内存流中 InputStream input = new ByteArrayInputStream(message.getBytes()); OutputStream output = new ByteArrayOutputStream(); int data = 0; // 每次读取一个数据 while ((data = input.read())!=-1){ output.write(Character.toUpperCase(data)); } System.out.println(output); // HELLO JAVA output.close(); input.close(); }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24

82 管道流

发送信息 <- 管道 -> 接收信息

  
 
  • 1

字节管道流 PipedInputStream, PipedOutputStream
字符管道流 PipedReader, PipedWriter

继承关系

InputStream -PipedInputStream

OutputStream -PipedOutputStream

Reader -PipedReader

Writer -PipedWriter

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11

管道发送接收数据

import java.io.*;

class Sender implements Runnable { private PipedOutputStream output; public Sender() { this.output = new PipedOutputStream(); } @Override public void run() { try { this.output.write("你好".getBytes()); } catch (IOException e) { e.printStackTrace(); } try { this.output.close(); } catch (IOException e) { e.printStackTrace(); } } public PipedOutputStream getOutput() { return this.output; }
}

class Receiver implements Runnable { private PipedInputStream input; public Receiver() { this.input = new PipedInputStream(); } @Override public void run() { try { byte[] data = new byte[1024]; int len = this.input.read(data); System.out.println(new String(data, 0, len)); // 你好 } catch (IOException e) { e.printStackTrace(); } try { this.input.close(); } catch (IOException e) { e.printStackTrace(); } } public PipedInputStream getInput() { return this.input; }
}

class Demo { public static void main(String[] args) throws IOException { Sender sender = new Sender(); Receiver receiver = new Receiver(); // 管道连接 sender.getOutput().connect(receiver.getInput()); new Thread(sender).start(); new Thread(receiver).start(); }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74

83 RandomAccessFile

随机读取类,可以移动文件指针

public RandomAccessFile(String name, String mode)

  
 
  • 1
import java.io.*;

class Demo { public static void main(String[] args) throws IOException { // 写入 RandomAccessFile writer = new RandomAccessFile("demo.txt", "rw"); writer.write("你好世界".getBytes()); writer.close(); // 读取 RandomAccessFile reader = new RandomAccessFile("demo.txt", "rw"); String line; while ((line = reader.readLine()) != null) { System.out.println(line); } writer.close(); }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19

第18 章 : 输入与输出支持

84 打印流

设计思想:装饰设计模式
为OutputStream 类实现一层包装
PrintStream
PrintWriter

继承关系

OutputStream -FilterOutputStream -PrintStream
Writer -PrintWriter

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
import java.io.*;

class Demo { public static void main(String[] args) throws IOException { PrintWriter writer = new PrintWriter(new FileWriter("demo.txt")); // 换行输出 writer.println("你好"); // 格式化输出 writer.printf("姓名 %s, 年龄: %s", "小强", 23); writer.close(); }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16

只要是文件内容输出时都使用打印流

85 System类对IO的支持

System是系统类
1、标准输出(显示器)
2、错误输出
3、标准输入(键盘)

public final class System { public final static InputStream in = null; public final static PrintStream out = null; // 黑色字体 public final static PrintStream err = null; // 红色字体
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5

修改输出位置

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.PrintStream;

class Demo { public static void main(String[] args) throws IOException { System.setErr(new PrintStream(new FileOutputStream(new File("demo.txt")))); System.err.println("你好"); }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11

接收键盘输入(一般不用此方法)

import java.io.IOException;
import java.io.InputStream;

class Demo { public static void main(String[] args) throws IOException { InputStream input = System.in; System.out.println("请输入姓名:"); byte[] data = new byte[1024]; int len = input.read(data); System.err.println(new String(data, 0, len)); }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13

86 BufferedReader缓冲输入流

JDK < 1.5

缓冲字符输入流
继承关系

Reader -BufferedReader

  
 
  • 1
  • 2

代码示例

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;

class Demo { public static void main(String[] args) throws IOException { BufferedReader reader = new BufferedReader(new InputStreamReader(System.in)); System.out.println("请输入:"); String msg = reader.readLine(); System.out.println(msg); }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12

87 Scanner扫描流

JDK > 1.5
替代BufferedReader

构造函数
判断是否有数据 public boolean hasNext()
读取数据 public String next()
设置分隔符

import java.io.IOException;
import java.util.Scanner;

class Demo { public static void main(String[] args) throws IOException { Scanner scanner = new Scanner(System.in); System.out.println("请输入年龄:"); if(scanner.hasNextInt()){ int age = scanner.nextInt(); System.out.println("您输入的年龄是:" + age); } else{ System.out.println("输入不正确"); } scanner.close(); }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16

可以结合正则进行判断验证

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Scanner;

class Demo { public static void main(String[] args) throws ParseException { Scanner scanner = new Scanner(System.in); System.out.println("请输入生日:"); if (scanner.hasNext("\\d{4}-\\d{2}-\\d{2}")) { String msg = scanner.next("\\d{4}-\\d{2}-\\d{2}"); System.out.println("您输入的年龄是:" + new SimpleDateFormat("yyyy-MM-dd").parse(msg)); } else { System.out.println("输入不正确"); } scanner.close(); }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19

读取文件

import java.io.File;
import java.io.FileNotFoundException;
import java.util.Scanner;

class Demo { public static void main(String[] args) throws FileNotFoundException { Scanner scanner = new Scanner(new File("demo.txt")); // 设置换行分隔符 // scanner.useDelimiter("\n"); while (scanner.hasNext()) { System.out.println(scanner.next()); } scanner.close(); }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18

开发中:
输出使用PrintWriter打印流
输入使用Scanner扫描流

第19 章 : 对象序列化

88 对象序列化基本概念

对象序列化:
将内存中保存的对象以二进制数据的形式处理,
实现对象的保存或者网络传输

 保存到文件
堆内存 - 二进制转换 ->  保存到数据库 发送到服务器

  
 
  • 1
  • 2
  • 3

要序列化的对象必须实现java.io.Serializable 接口
没有任何方法,只是描述一种能力

示例

import java.io.Serializable;


class Person implements Serializable { private String name; private int age; public Person(String name, int age) { this.name = name; this.age = age; }
}


  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13

89 序列化与反序列化处理

继承关系

InputStream(ObjectInput, ObjectStreamConstants) -ObjectInputStream

OutputStream(ObjectOutput, ObjectStreamConstants) -ObjectOutputStream

  
 
  • 1
  • 2
  • 3
  • 4
  • 5

代码示例

import java.io.*;

class Person implements Serializable { private String name; private int age; public Person(String name, int age) { this.name = name; this.age = age; }
}

class Demo { private static final File  SAVE_FILE = new File("demo.person"); public static void main(String[] args) throws IOException, ClassNotFoundException { Person person = new Person("Tom", 23); // saveObject(person); System.out.println(loadObject()); // Person@15aeb7ab } // 序列化 public static void saveObject(Object obj) throws IOException { ObjectOutputStream oos = new ObjectOutputStream(new FileOutputStream(SAVE_FILE)); oos.writeObject(obj); oos.close(); } // 反序列化 public static Object loadObject() throws IOException, ClassNotFoundException { ObjectInputStream ois = new ObjectInputStream(new FileInputStream(SAVE_FILE)); Object obj = ois.readObject(); ois.close(); return obj; }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38

实际开发中不直接操作ObjectInputStream、ObjectOutputStream

90 transient关键字

表示进行序列化处理时,不处理被transient关键字修饰的字段
不常用,知道即可

IO继承体系整合

// 字节流:
OutputStream(Closeable, Flushable) -FileOutputStream -ByteArrayOutputStream -PipedOutputStream -FilterOutputStream -PrintStream -ObjectOutputStream


InputStream(Closeable) -FileInputStream -ByteArrayInputStream -PipedInputStream -ObjectInputStream

// 字符流:
Writer(Appendable, Closeable, Flushable) -OutputStreamWriter -FileWriter -CharArrayWriter -PipedReader -PrintWriter -BufferedWriter

Reader(Readable, Closeable) -InputStreamReader -FileReader -CharArrayReader -PipedWriter -BufferedReader

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31

文章来源: pengshiyu.blog.csdn.net,作者:彭世瑜,版权归原作者所有,如需转载,请联系作者。

原文链接:pengshiyu.blog.csdn.net/article/details/103649236

【版权声明】本文为华为云社区用户转载文章,如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。