Java 字符流

目录

字符流

1.为什么会出现字符流?

2.编码表

3.字符串的编码解码问题

4.字符流的编码解码问题

 5.字符流写数据的5种方式

6.字符流读数据的两种方式

7.案例:复制Java文件

8.改进案例

9.字符缓冲流

10.案例(字符缓冲流改进版)

11.字符缓冲流的特有功能

12.案例(字符缓冲流特有功能改进)

13.IO流小结

14.集合到文件

15.文件到集合

16.点名器

17.集合到文件(改进)

18.文件到集合(改进)

19.集合到文件(数据排序改进版)

20.案例:复制单级文件夹

21.案例:复制多级文件夹


1.为什么会出现字符流?

        汉字存储问题:一个汉字存储,如果是GBK编码,占用2个字节;如果是UTF-8编码,占用三个字节。所以使用单个字节进行传输时,汉字会被拆分成两个或者三个字节单独输出,会变成乱码。为了解决这个问题,引入了字符流。

        在使用字节流传输文字时,由于底层会自动拼接,也能传输汉字。系统判别字节是否是汉字的依据是,汉字存储时的第一个字节时负数,当检测到负数时,就代表这是汉字字符,进而进行字节拼接。得到汉字字符。

由于字节流操作中文不方便,因此,Java提供了字符流。字符流=字节流+编码表。


2.编码表

需要知道:计算机啊存储的信息都是用二进制表示的。

编码与解码。

字符编码;就是一套自然语言的字符与二进制数之间的对应规则。

字符集:系统支持的所有字符的集合,例如ASCII字符集,GBXXX字符集。

GB2313:GB2313是中华人民共和国使用的字符编码标准。这是一种支持多种汉字的2字节编码方案。GB2313包括简体中文和繁体中文,以及中文文本中常用的标点符号和其他符号。它于1980年由中国国家技术监督局首次引入,此后在中国大陆被广泛采用。

GBK:GB2313的扩展,最常用的,重点掌握。

Unicode字符集(Unicode Character Set)是一种用于表示文本字符的国际标准,旨在为世界上所有已知的书写系统提供一个唯一的数字代码,以便在任何计算机或设备上进行交换和处理。这个标准涵盖了大量字符集,包括拉丁字母、希腊字母、西里尔字母、中文、日文、韩文等等。Unicode字符集的编码格式可以为UTF-8、UTF-16和UTF-32等。在计算机领域中,Unicode字符集得到了广泛的应用,特别是在网页设计、软件开发、数据库处理等方面。

UTF-8是一种变长的字符编码标准,它可以表示Unicode标准中的任意字符,它使用1到4个字节来表示一个字符,具体长度取决于字符的Unicode编码值。UTF-8编码的特点是向后兼容ASCII码,即使用UTF-8编码的文本可以被ASCII编码的软件直接处理,同时也支持多语言字符集,因此被广泛应用于互联网上的各种应用和协议中。

UTF-8是一种可变长度字符编码,用于Unicode字符集的编码。它的编码规则如下:

  1. 对于0x0000到0x007F之间的字符,用一个字节表示,最高位为0;

  2. 对于0x0080到0x07FF之间的字符,用两个字节表示,最高位为110,次高位为10;

  3. 对于0x0800到0xFFFF之间的字符,用三个字节表示,最高位为1110,次高位为10,第三位为10;

  4. 对于0x10000到0x10FFFF之间的字符,用四个字节表示,最高位为11110,次高位为10,第三位为10,第四位为10。

UTF-8编码的优点是兼容ASCII编码,对于ASCII字符只需要一个字节表示,而对于非ASCII字符则需要多个字节表示。同时,UTF-8编码也支持任意Unicode字符。


3.字符串的编码解码问题

String s = "中国";
byte[] bytes = s.getBytes("GBK");//[-42, -48, -71, -6]
String ss = new String(bytes,"GBK");//中国


编码与解码使用的字符集需一致。反例如下:

String s = "中国";
byte[] bytes = s.getBytes("GBK");//[-42, -48, -71, -6]
String ss = new String(bytes,"UTF-8");//�й�乱码

 

4.字符流的编码解码问题

字符流抽象类:

Reader:字符输入流的抽象类

Writer:字符输出流的抽象类

相关类:

InputStreamReader:从字节流到字符流,使用的字符集可以指定

OutputStreamWriter:从字符流到字节流,字符集可以指定

OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("myCharStream\\osw.txt"));
osw.write("中文");
osw.close();
        OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("myCharStream\\osw.txt"),"GBK");
        osw.write("中文");
        osw.close();

        InputStreamReader isr = new InputStreamReader(new FileInputStream("myCharStream\\osw.txt"),"GBK");
        int ch;
        while((ch = isr.read())!= -1) {
            System.out.print((char)ch);//中文
        }
        isr.close();

 

 5.字符流写数据的5种方式

01

        OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("myCharStream\\osw.txt"));
        osw.write(97);
        osw.close();

02

        OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("myCharStream\\osw.txt"));
        char [] arr = {'a','b','c','d','e'};
        osw.write(arr);
        osw.close();

03

        OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("myCharStream\\osw.txt"));
        char [] arr = {'a','b','c','d','e'};
        osw.write(arr,1, 3);
        osw.close();

04

        OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("myCharStream\\osw.txt"));
        String s = "abcde";
        osw.write(s);
        osw.close();

05

        OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("myCharStream\\osw.txt"));
        String s = "abcde";
        osw.write(s,1,4);
        osw.close();

 

6.字符流读数据的两种方式

01

        InputStreamReader isr = new InputStreamReader(new FileInputStream("myCharStream\\osw.txt"));
        int ch;
        while ((ch = isr.read()) != -1) {
            System.out.print((char) ch);
        }

        isr.close();

02

        InputStreamReader isr = new InputStreamReader(new FileInputStream("myCharStream\\osw.txt"));
        char [] chars = new char[1024];
        int len;
        while ((len = isr.read(chars))!= -1) {
            System.out.println(new String(chars,0,len));
        }

        isr.close();

 

7.案例:复制Java文件

package com.itheima03;

import java.io.*;

//需求
//把模块目录下的ConversionStreamDemo.java复制到模块目录下的Copy.java
public class Demo {
    public static void main(String[] args) throws IOException {
        InputStreamReader isr = new InputStreamReader(new FileInputStream("myCharStream\\src\\com\\itheima02\\ConversionStreamDemo.java"));
        OutputStreamWriter osr = new OutputStreamWriter(new FileOutputStream("myCharStream\\Copy.java"));
//读取字符数组
//        char [] chars = new char[1024];
//        int len;
//        while ((len = isr.read(chars))!= -1) {
//            osr.write(chars,0,len);
//        }
//        读取一个字符
        int ch;
        while ((ch = isr.read()) != -1) {
            osr.write(ch);
        }
        osr.close();
        isr.close();

    }
}

 

8.改进案例

FileWriter与FileReader

package com.itheima03;

import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;

public class Demo02 {
    public static void main(String[] args) throws IOException {
        FileReader fr = new FileReader("myCharStream\\src\\com\\itheima02\\ConversionStreamDemo.java");
        FileWriter fw = new FileWriter("myCharStream\\Copy.java");
//        int ch;
//        while ((ch = fr.read())!= -1) {
//            fw.write(ch);
//        }
        char[] chars = new char[1024];
        int len;
        while ((len = fr.read(chars)) != -1) {
            fw.write(chars, 0, len);
        }

        fr.close();
        fw.close();
    }
}

 

9.字符缓冲流

package com.itheima04;

import java.io.*;

public class BufferedStreamDemo01 {
    public static void main(String[] args) throws IOException {
//        BufferedWriter bw = new BufferedWriter(new FileWriter("myCharStream\\bw.txt"));
//        bw.write("hello\n");
//        bw.write("world\n");
//        bw.write("java\n");
//        bw.close();
        BufferedReader br = new BufferedReader(new FileReader("myCharStream\\bw.txt"));
//        int ch;
//        while ((ch = br.read())!= -1) {
//            System.out.print((char) ch);
//        }
        char[] chars = new char[1024];
        int len;
        while ((len = br.read(chars)) != -1) {
            System.out.print(new String(chars, 0, len));
        }

        br.close();

    }
}

 

10.案例(字符缓冲流改进版)

package com.itheima04;

import java.io.*;

public class Demo01 {
    public static void main(String[] args) throws IOException {
        BufferedReader br = new BufferedReader(new FileReader("myCharStream\\src\\com\\itheima02\\ConversionStreamDemo.java"));
        BufferedWriter bw = new BufferedWriter(new FileWriter("myCharStream\\Copy.java"));

        //01
//        int ch;
//        while ((ch = br.read())!= -1) {
//            bw.write(ch);
//        }
        //02
        char[] chars = new char[1024];
        int len;
        while ((len = br.read(chars)) != -1) {
            bw.write(chars, 0, len);
        }

        br.close();
        bw.close();

    }
}

 

11.字符缓冲流的特有功能

package com.itheima04;

import java.io.*;

public class Demo02 {
    public static void main(String[] args) throws IOException {
/*        BufferedWriter bw = new BufferedWriter(new FileWriter("myCharStream\\bw.txt"));

        for (int i=0;i<10;i++) {
            bw.write("hello"+i);
            bw.newLine();
            bw.flush();
        }
        bw.close();*/
        BufferedReader br = new BufferedReader(new FileReader("myCharStream\\bw.txt"));

        String line;
        while ((line = br.readLine())!= null) {
            System.out.println(line);
        }

        br.close();
    }
}

 

12.案例(字符缓冲流特有功能改进)

import java.io.*;

public class Demo03 {
    public static void main(String[] args) throws IOException {
        BufferedReader br = new BufferedReader(new FileReader("myCharStream\\src\\com\\itheima02\\ConversionStreamDemo.java"));
        BufferedWriter bw = new BufferedWriter(new FileWriter("myCharStream\\Copy.java"));

        String line;

        while ((line = br.readLine())!= null) {
            bw.write(line);
            bw.newLine();
            bw.flush();
        }
        br.close();
        bw.close();
    }

}

 

13.IO流小结

字节流可以复制任意文件数据,有4种方式一般采用字节缓冲流一次读写一个字节数组的方式。

字符流只能复制文本数据,有5种方式,一般采用字符缓冲流的特有功能。


 

14.集合到文件

import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;

//集合到文件
public class Demo {
    public static void main(String[] args) throws IOException {
        ArrayList<String> list = new ArrayList<>();
        list.add("hello");
        list.add("world");
        list.add("Java");

        BufferedWriter bw = new BufferedWriter(new FileWriter("myCharStream\\list.txt"));

        for (String s : list) {
            bw.write(s);
            bw.newLine();
            bw.flush();
        }
        bw.close();
    }
}

 

15.文件到集合

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.AbstractList;
import java.util.ArrayList;

public class Demo02 {
    public static void main(String[] args) throws IOException {
        BufferedReader br = new BufferedReader(new FileReader("myCharStream\\list.txt"));
        AbstractList<String> list = new ArrayList<>();

        String line;
        while ((line = br.readLine())!= null) {
            list.add(line);
        }
        br.close();
        System.out.println(list);
    }
}

 

16.点名器

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Random;

public class Demo03 {
    public static void main(String[] args) throws IOException {
        BufferedReader br = new BufferedReader(new FileReader("myCharStream\\name.txt"));
        ArrayList<String> list = new ArrayList<>();

        String s;
        while ((s = br.readLine())!= null) {
            list.add(s);
        }
        br.close();
        Random random = new Random();
        int index = random.nextInt(0, list.size());

        String name = list.get(index);
        System.out.println(name);
    }
}

 

17.集合到文件(改进)

import java.util.Objects;

public class Student {
    private String sid;
    private String name;
    private int age;
    private String ads;

    public Student() {
    }

    public Student(String sid, String name, int age, String ads) {
        this.sid = sid;
        this.name = name;
        this.age = age;
        this.ads = ads;
    }

    public String getSid() {
        return sid;
    }

    public void setSid(String sid) {
        this.sid = sid;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public String getAds() {
        return ads;
    }

    public void setAds(String ads) {
        this.ads = ads;
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;

        Student student = (Student) o;

        if (age != student.age) return false;
        if (!Objects.equals(sid, student.sid)) return false;
        if (!Objects.equals(name, student.name)) return false;
        return Objects.equals(ads, student.ads);
    }

    @Override
    public int hashCode() {
        int result = sid != null ? sid.hashCode() : 0;
        result = 31 * result + (name != null ? name.hashCode() : 0);
        result = 31 * result + age;
        result = 31 * result + (ads != null ? ads.hashCode() : 0);
        return result;
    }
}
import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;

public class Demo {
    public static void main(String[] args) throws IOException {
        ArrayList<Student> list = new ArrayList<>();
        Student s1 = new Student("23001", "路飞", 23, "风车村");
        Student s2 = new Student("23002", "山治", 23, "巴拉蒂");
        Student s3 = new Student("23003", "娜美", 23, "橘子镇");
        Student s4 = new Student("23004", "乔巴", 23, "磁鼓国");
        Student s5 = new Student("23005", "弗兰奇", 23, "水之都");
        list.add(s1);
        list.add(s2);
        list.add(s3);
        list.add(s4);
        list.add(s5);

        BufferedWriter bw = new BufferedWriter(new FileWriter("myCharStream\\student.txt"));

        for (Student s : list) {
            StringBuilder sb = new StringBuilder();
            sb.append(s.getSid()).append(',').append(s.getName()).append(',').append(s.getAge()).append(',').append(s.getAds());
            String line = sb.toString();
            bw.write(line);
            bw.newLine();
            bw.flush();
        }
        bw.close();

    }
}  }
}
23001,路飞,23,风车村
23002,山治,23,巴拉蒂
23003,娜美,23,橘子镇
23004,乔巴,23,磁鼓国
23005,弗兰奇,23,水之都

 

18.文件到集合(改进)

package com.itheima06;

import java.util.Objects;

public class Student {
    private String sid;
    private String name;
    private int age;
    private String ads;

    public Student() {
    }

    public Student(String sid, String name, int age, String ads) {
        this.sid = sid;
        this.name = name;
        this.age = age;
        this.ads = ads;
    }

    public String getSid() {
        return sid;
    }

    public void setSid(String sid) {
        this.sid = sid;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public String getAds() {
        return ads;
    }

    public void setAds(String ads) {
        this.ads = ads;
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;

        Student student = (Student) o;

        if (age != student.age) return false;
        if (!Objects.equals(sid, student.sid)) return false;
        if (!Objects.equals(name, student.name)) return false;
        return Objects.equals(ads, student.ads);
    }

    @Override
    public int hashCode() {
        int result = sid != null ? sid.hashCode() : 0;
        result = 31 * result + (name != null ? name.hashCode() : 0);
        result = 31 * result + age;
        result = 31 * result + (ads != null ? ads.hashCode() : 0);
        return result;
    }

    @Override
    public String toString() {
        return "Student{" +
                "sid='" + sid + '\'' +
                ", name='" + name + '\'' +
                ", age=" + age +
                ", ads='" + ads + '\'' +
                '}';
    }
}
package com.itheima06;

import java.io.*;
import java.util.ArrayList;

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

        BufferedReader br = new BufferedReader(new FileReader("myCharStream\\student.txt"));
        ArrayList<Student> list = new ArrayList<>();

        String line;
        while ((line = br.readLine()) != null) {
            String[] strings = line.split(",");
            Student s = new Student();
            s.setSid(strings[0]);
            s.setName(strings[1]);
            s.setAge(Integer.parseInt(strings[2]));
            s.setAds(strings[3]);
            list.add(s);

        }
        br.close();
        for (Student s : list) {
            System.out.println(s);
        }


    }
}
Student{sid='23001', name='路飞', age=23, ads='风车村'}
Student{sid='23002', name='山治', age=23, ads='巴拉蒂'}
Student{sid='23003', name='娜美', age=23, ads='橘子镇'}
Student{sid='23004', name='乔巴', age=23, ads='磁鼓国'}
Student{sid='23005', name='弗兰奇', age=23, ads='水之都'}

 

19.集合到文件(数据排序改进版)

public class Student {
    private String name;
    private int lit;
    private int math;
    private int eng;

    public Student() {
    }

    public Student(String name, int lit, int math, int eng) {
        this.name = name;
        this.lit = lit;
        this.math = math;
        this.eng = eng;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getLit() {
        return lit;
    }

    public void setLit(int lit) {
        this.lit = lit;
    }

    public int getMath() {
        return math;
    }

    public void setMath(int math) {
        this.math = math;
    }

    public int getEng() {
        return eng;
    }

    public void setEng(int eng) {
        this.eng = eng;
    }

    public int sum() {
        return lit + math + eng;
    }
}
import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;
import java.util.Comparator;
import java.util.Scanner;
import java.util.TreeSet;

public class Demo {
    public static void main(String[] args) throws IOException {
        BufferedWriter br = new BufferedWriter(new FileWriter("myCharStream\\rankList"));
        TreeSet<Student> set = new TreeSet<>(new Comparator<Student>() {
            @Override
            public int compare(Student s1, Student s2) {
                int sum = s2.sum() - s1.sum();
                int sum2 = (sum == 0) ? s2.getLit() - s1.getLit() : sum;
                int sum3 = (sum2 == 0) ? s2.getMath() - s1.getMath() : sum2;
                int sum4 = (sum3 == 0) ? s2.getName().compareTo(s1.getName()) : sum3;
                return sum4;
            }
        });
        for (int i = 0; i < 5; i++) {
            System.out.println("请录入第" + (i + 1) + "位学生");
            Student s = getScore();
            set.add(s);
        }
        for (Student s : set) {
            StringBuilder sb = new StringBuilder();
            sb.append(s.getName()).append(",").append(s.getLit()).append(",").append(s.getMath()).append(",").append(s.getEng());
            String line = sb.toString();
            br.write(line);
            br.newLine();
            br.flush();
        }
        br.close();
    }

    public static Student getScore() {
        Student s = new Student();
        Scanner sc = new Scanner(System.in);
        System.out.println("请输入学生姓名");
        String name = sc.nextLine();
        s.setName(name);
        System.out.println("请输入语文成绩");
        int lit = sc.nextInt();
        s.setLit(lit);
        System.out.println("请输入数学成绩");
        int math = sc.nextInt();
        s.setMath(math);
        System.out.println("请输入英语成绩");
        int eng = sc.nextInt();
        s.setEng(eng);
        System.out.println("录入完毕");
        return s;
    }
}

 

20.案例:复制单级文件夹

import java.io.*;

public class Demo {
    public static void main(String[] args) throws IOException {
        //创建数据源目录数据对象
        File scrFolder = new File("E:\\itcast");

        //获取数据源目录File对象的名称
        String scrFolderName = scrFolder.getName();
        
        //创建目的地目录File对象
        File destFolder = new File("myCharStream", scrFolderName);

        //判断目的地目录对应的File是否存在,如果不存在就创建
        boolean exists = destFolder.exists();
        if (!exists) {
            destFolder.mkdir();
        }

        //获取数据源目录下的所有文件的File数组
        File[] files = scrFolder.listFiles();

        //遍历File数组,得到每一个File对象,其实就是数据源文件
        for (File scrFile : files) {
            //数据源文件:E:\\itcast\\mn.jpg
            String scrFileName = scrFile.getName();
            //获取目的地文件File对象,路径名是目的地目录+filename组成
            File destFile = new File(destFolder, scrFileName);
            //复制文件
            copyFile(scrFile, destFile);

        }


    }

    public static void copyFile(File scrFile, File destFile) throws IOException {
        BufferedInputStream bis = new BufferedInputStream(new FileInputStream(scrFile));
        BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(destFile));
        //复制文件
        byte[] bytes = new byte[1024];
        int len;
        while ((len = bis.read(bytes)) != -1) {
            bos.write(bytes,0,len);
        }
        bos.close();
        bis.close();

    }
}

 

21.案例:复制多级文件夹

import java.io.*;

public class Demo {
    public static void main(String[] args) throws IOException {
        //创建源文件,目的地文件
        File scrFile = new File("E:\\itcast");
        File destFile = new File("F:\\");
        //写方法实现文件夹的复制
        copyFolder(scrFile, destFile);


    }

    public static void copyFile(File scrFile, File destFile) throws IOException {
        BufferedInputStream bis = new BufferedInputStream(new FileInputStream(scrFile));
        BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(destFile));

        byte[] bytes = new byte[1024];
        int len;
        while ((len = bis.read(bytes)) != -1) {
            bos.write(bytes, 0, len);
        }
        bis.close();
        bos.close();
    }

    //复制文件夹
    public static void copyFolder(File scrFile, File destFile) throws IOException {
        if (scrFile.isDirectory()) {

            String scrFolderName = scrFile.getName();
            File newFolder = new File(destFile, scrFolderName);
            if (!newFolder.exists()) {
                newFolder.mkdir();
            }
            File[] files = scrFile.listFiles();
            for (File file : files) {
                //把该File作为数据源File对象,递归调用复制文件夹的方法
                copyFolder(file,newFolder);
            }
        } else {
            File newFile = new File(destFile,scrFile.getName());
            copyFile(scrFile, newFile);
        }

    }

}

  • 11
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值