JAVA之IO流、String中的编程问题、转换流、序列化流

    xiaoxiao2022-07-05  187

    1.IO流

    1.1IO流概念及其分类

    1.1.1IO流概念

    IO流用于处理设备之间的数据传输。

    JAVA对数据的操作是通过流的方式。

    JAVA用于操作流的对象都在IO包中。

    1.1.2IO流分类

    a.按照数据流向

    输入流 读入数据

    输出流 读出数据

    b.按照数据类型

    字节流 可以读写任何类型的文件

    字符流 只能读写文本文件

    不清楚该用什么,就用字节流。

    1.2IO流基本类和FileOutoutStream

    1.2.1IO流基本类概念

    a.字节流的抽象类

    InputStream ,OutputStream。

    b.字符流的抽象基类

    Reader , Writer。

    注意:

    由这四个类派生出来的子类名称都是以其父类名作为子类名的后缀。

    案例:

    往一个文本文件中写一串数据 Hello,IO

    因为我们要写数据,所以我们应该使用字节流中输出流    OutputStream

    package westos; import java.io.*; public class MyTest1 { //往一个文本文件中写一串数据 Hello,IO public static void main(String[] args) throws IOException{ FileOutputStream out = new FileOutputStream("a.txt"); out.write("HELLO IO".getBytes()); out.close(); } }

    结果:

     

    1.2.2FileOutputStream的三个write()方法以及换行和追加写入

    package westos; import java.io.*; public class MyTest1 { public static void main(String[] args) throws IOException{ FileOutputStream out = new FileOutputStream("a.txt",true);\\true的作用是实现数据的追加写入 out.write("\r\n".getBytes());\\windows下的换行符是 \r\n( Linux下的换行符是\n,Mac下的换行符是\r)   out.write(97);//写一个字节 超过一个字节 砍掉前面的字节 out.write(98); out.write(99); /*......................................*/ out.write("\r\n".getBytes()); out.write(new byte[]{65,66,67});//写一个字节数组 /*......................................*/ out.write("\r\n如果没有见过光明,我本可以忍受黑暗".getBytes(),0,26);//写一个字节数组的一部分 out.write("\r\n如果没有见过光明,我本可以忍受黑暗".getBytes(),0,53); out.close(); } }

    结果:

    1.2.3写出数据加入异常处理

    package westos; import java.io.*; public class MyTest1 { public static void main(String[] args) { FileOutputStream out = null; try { out = new FileOutputStream("a.txt",true); out.write(97); out.write(98); out.write(99); } catch (IOException e) { e.printStackTrace(); }finally { try { if (out != null) { out.close(); } } catch (IOException e) { e.printStackTrace(); } } } }

    1.3FileInputStream

    1.3.1读取数据一次一个字节和读取数据一次一个字节数组

    package westos; import java.io.*; public class MyTest1 { public static void main(String[] args) throws IOException{ FileOutputStream out = new FileOutputStream("a.txt"); out.write("a如果没有见过光明,我本可以忍受黑暗".getBytes()); out.close(); FileInputStream in = new FileInputStream(new File("a.txt"));; int a = in.read();//一次读取一个字节 System.out.println(a);//如果没有数据返回的就是-1 byte[] b = new byte[1024];//把文件中的数据,读取到容器中,返回值是,读取到的有效字节个数 int c = in.read(b); System.out.println(c); String s = new String(b, 0, c); System.out.println(s); in.close(); } }

    结果:

    97 51 如果没有见过光明,我本可以忍受黑暗

    1.4字节流复制

    1.4.1复制文件

    package westos; import java.io.*; public class MyTest1 { public static void main(String[] args) throws IOException{ FileInputStream in = new FileInputStream("a.txt"); //关联目标文件 FileOutputStream out = new FileOutputStream("F:\\Test 3\\a2.txt"); //循环的读写 int len=0; while ((len=in.read())!=-1){ out.write(len); out.flush();//刷新 } //释放资源 in.close(); out.close(); } }

    1.4.2复制MP3

    package westos; import java.io.*; public class MyTest1 { public static void main(String[] args) throws IOException{ //我们读取一个字节,写入一个字节,来复制音频文件 FileInputStream in = new FileInputStream("F:\\Test1\\城府.mp3"); FileOutputStream out = new FileOutputStream("F:\\Test 3\\城府1.mp3"); int len=0;//定义一个变量,记录读取到的字节 //循环读写 while ((len=in.read())!=-1){ out.write(len); out.flush(); } //释放资源 in.close(); out.close(); } }

    1.4.3结果

    1.5BufferedInputStream读取数据

    package westos; import java.io.*; public class MyTest1 { public static void main(String[] args) throws IOException{ BufferedInputStream b = new BufferedInputStream(new FileInputStream("a.txt")); byte[] bytes = new byte[52]; int q=0; while ((q=b.read(bytes))!=-1){ b.read(bytes,0,q);\\高效的字符输入流 //高效的字符输出流:    BufferedWriter } System.out.println(new String(bytes)); } }

    结果:

    a如果没有见过光明,我本可以忍受黑暗

    1.6练习

    1.6.1把集合中的数据存储到文本文件

    package westos; import java.io.*; import java.util.ArrayList; public class MyTest1 { public static void main(String[] args) throws IOException{ ArrayList<String> list = new ArrayList<>(); list.add("李一 "); list.add("张三"); list.add("宁一"); list.add("徐四"); list.add("刘五"); list.add("李二 "); list.add("张四"); list.add("宁二"); list.add("徐五"); list.add("刘六"); //遍历集合,取出数据写入文本文件 BufferedWriter writer = new BufferedWriter(new FileWriter("a.txt")); for (String s : list) { writer.write(s); writer.newLine(); writer.flush(); } writer.close(); } }

    结果:

    1.6.2随机获取文本文件中的姓名

    package westos; import java.io.*; import java.util.ArrayList; import java.util.Random; public class MyTest1 { public static void main(String[] args) throws IOException{ BufferedReader bfr = new BufferedReader(new FileReader("a.txt")); ArrayList<String> list = new ArrayList<>(); while (true) { String s = bfr.readLine(); if (s != null) { list.add(s); } else { break; } } // System.out.println(list);\\输出[李一 , 张三, 宁一, 徐四, 刘五, 李二 , 张四, 宁二, 徐五, 刘六] Random random = new Random(); //生成一个随机索引 int index = random.nextInt(list.size()); String s = list.get(index); System.out.println(s);//随机输出 } }

    结果:

    在“a.txt”中随机输出一个名字

    1.6.3复制指定目录下指定后缀名的文件并修改名称

    package westos; import java.io.*; public class MyTest1 { public static void main(String[] args) throws IOException { File f1 = new File("F:\\Test 2\\fff"); File[] f2 = f1.listFiles(new FileFilter() { @Override public boolean accept(File pathname) { //System.out.println(pathname); if (pathname.isFile() && pathname.getName().endsWith(".png")) { return true; } else { return false; }//筛选出后缀为".png"的文件 } }); FileInputStream in = null; FileOutputStream out= null; for (File j : f2) { String str1 = j.getName(); String str2 = j.getName().replace(".png", ".jpg"); //File f3 = new File("F:\\Test 2\\fff\\" + str2); in = new FileInputStream("F:\\Test 2\\fff\\" + str1); out = new FileOutputStream("F:\\Test 3\\"+ str2); int len = 0;//定义一个变量,记录读取到的字节 //循环读写 while ((len = in.read()) != -1) { out.write(len); out.flush(); } } //释放资源 in.close(); out.close(); } }

    要复制照片:

    复制完成:

    1.6.4键盘录入学生信息按照总分排序并写入文本文件

    package Asd; import java.io.BufferedWriter; import java.io.FileWriter; import java.io.IOException; import java.text.SimpleDateFormat; import java.util.Comparator; import java.util.Date; import java.util.Scanner; import java.util.TreeSet; public class MyTest { public static void main(String[] args) throws IOException { TreeSet<Student> treeSet = new TreeSet<>(new Comparator<Student>() { @Override public int compare(Student s1, Student s2) { //按照总分来排序 int num = s1.getTotalScore() - s2.getTotalScore(); int num2 = num == 0 ? s1.getName().compareTo(s2.getName()) : num; return -num2; } }); for (int i = 1; i <= 3; i++) { Scanner sc = new Scanner(System.in); System.out.println("请输入第" + i + "个学生的姓名"); String name = sc.nextLine(); Student student = new Student(); student.setName(name); System.out.println("请输入第" + i + "个学生的语文成绩"); int yw = sc.nextInt(); student.setChineseScore(yw); System.out.println("请输入第" + i + "个学生的数学成绩"); int sx = sc.nextInt(); student.setMathScore(sx); System.out.println("请输入第" + i + "个学生的英语成绩"); int yy = sc.nextInt(); student.setEnglishScore(yy); //把学生添加到集合里面 treeSet.add(student); } //把集合中的数据存到文本文件中存起来 long time = System.currentTimeMillis(); Date date = new Date(time); SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH-mm-ss");//获取现在的时间 String s = simpleDateFormat.format(date); BufferedWriter bfw = new BufferedWriter(new FileWriter(s+".txt",true)); bfw.write("序号 姓名 语文成绩 数学成绩 英语成绩 总分"); bfw.newLine(); bfw.flush(); //遍历 int index = 1; for (Student student : treeSet) { bfw.write(index + " " + student.getName() + " " + student.getChineseScore() + " " + student.getMathScore() + " " + student.getEnglishScore() + " " + student.getTotalScore()); bfw.newLine(); bfw.flush(); index++; } bfw.close(); System.out.println("学生成绩录入完成"); } } package Asd; public class Student { private String name; private int chineseScore; private int mathScore; private int englishScore; public String getName() { return name; } public void setName(String name) { this.name = name; } public int getChineseScore() { return chineseScore; } public void setChineseScore(int chineseScore) { this.chineseScore = chineseScore; } public int getMathScore() { return mathScore; } public void setMathScore(int mathScore) { this.mathScore = mathScore; } public int getEnglishScore() { return englishScore; } public void setEnglishScore(int englishScore) { this.englishScore = englishScore; } //获取总分的方法 public int getTotalScore() { return chineseScore + mathScore + englishScore; } }

    键盘录入:

    请输入第1个学生的姓名 qaz 请输入第1个学生的语文成绩 34 请输入第1个学生的数学成绩 45 请输入第1个学生的英语成绩 56 请输入第2个学生的姓名 wsx 请输入第2个学生的语文成绩 67 请输入第2个学生的数学成绩 78 请输入第2个学生的英语成绩 89 请输入第3个学生的姓名 edc 请输入第3个学生的语文成绩 12 请输入第3个学生的数学成绩 34 请输入第3个学生的英语成绩 56 学生成绩录入完成

    存入文本:

    1.7序列化流和反序列化流的概述和问题

    1.7.1序列化流和反序列化流的概述

    所谓的序列化:就是把对象通过流的方式存储到文件中。

    注意:此对象 要重写Serializable 接口才能被序列化。

    反序列化:就是把文件中存储的对象以流的方式还原成对象

    序列化流:    ObjectOutputStream

    反序列化流:    ObjectInputStream

    一个对象可以被序列化的前提是这个对象对应的类必须实现Serializable接口

    1.7.2序列化流时的黄色警告线问题

    我们的一个类可以被序列化的前提是需要这个类实现Serializable接口,就需要给这个类添加一个标记.

    在完成序列化以后,序列化文件中还存在一个标记,然后在进行反序列化的时候, 会验证这个标记和序列化前的标记是否一致,如果一致就正常进行反序列化,如果 不一致就报错了. 而现在我们把这个类做了修改,将相当于更改了标记,而导致这两个标记不一致,就报错了.

    解决问题: 只要让这个两个标记一致,就不会报错了

    最新回复(0)