IO流01_字节字符流缓冲流标准输入输出流打印流

Posted 所得皆惊喜

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了IO流01_字节字符流缓冲流标准输入输出流打印流相关的知识,希望对你有一定的参考价值。

文章目录

①. IO流概述及分类

  • ①. IO流用来处理设备之间的数据传输、Java堆数据的操作是通过流的方式 、Java用于操作流的类都在IO包中

  • ②. 输入input:读取外部数据(磁盘、光盘等存储设备的数据)到程序(内存)中
    输出output:将程序(内存)数据输出到磁盘、光盘等存储设备中

  • ③. 流的分类

  1. 流按流向分为两种:输入流(读数据)、输出流(写数据)
  2. 流按操作类型分为两种:(默认是这样方式)
    a. 字节流 [InputStream、OutputStrean]⇢抽象父类:字节流可以操作任何数据,因为计算机任何数据都是以字节的形式储存的(音频、视频、图片等)
    b. 字符流 [Reader、Writer]⇢抽象父类:字符流只能操作纯字符数据,比较方便
  3. 按流的角色的不同分为:节点流(没有进行包一层处理的如:FileInputStream),处理流(在字节流的基础上包了一层处理)
    a. 节点流:直接从数据源或目的地读写数据
    b. 处理流:不直接连接到数据源或目的地,而是“连接”在已存在的流(节点流或处理流)之上,通过对数据的处理为程序提供更为强大的读写功能
  • ④. IO流体系

②. 字节输入流 - FileInputStream

  • ①. FileInputStream 构造方法
  1. FileInputStream​(String name)
  2. FileInputStream​(File file)
  • ②. read方法
  1. int read():一次读取一个字节,如果文件读到末尾,返回值是-1
  2. int read(byte[ ] b):从此输入流中最多b.length 个字节的数据读入一个byte数组中
	FileInputStream fis=new FileInputStream("hello.txt");
	//循环从硬盘上读取
	int x;
	while((x=fis.read())!=-1)
	    System.out.print(x);
	
	//关闭资源
	fis.close();

③. 字节输出流 - FileOutputStream

  • ①. 构造方法
  1. FileOutputStream​(String name):创建文件输出流以指定的名称写入文件
  2. FileOutputStream​(File file):创建文件输出流以写入由指定的 File对象表示的文件
  • ②. writer方法
  1. void write​(int b):将指定的字节写入此文件输出流
  2. void write​(byte[] b):将 b.length字节从指定的字节数组写入此文件输出流
  3. void write​(byte[] b, int off, int len):将 len字节从指定的字节数组开始,从偏移量off开始写入此文件输出流一次写一个字节数组的部分数据
        //FileOutputStream​(String name):创建文件输出流以指定的名称写入文件
        FileOutputStream fos = new FileOutputStream("myByteStream\\\\fos.txt");
        //new File(name)
//        FileOutputStream fos = new FileOutputStream(new File("myByteStream\\\\fos.txt"));

        //FileOutputStream​(File file):创建文件输出流以写入由指定的 File对象表示的文件
      File file = new File("myByteStream\\\\fos.txt");
      FileOutputStream fos2 = new FileOutputStream(file);
//        FileOutputStream fos2 = new FileOutputStream(new File("myByteStream\\\\fos.txt"));

        //void write​(int b):将指定的字节写入此文件输出流
//        fos.write(97);
//        fos.write(98);
//        fos.write(99);
//        fos.write(100);
//        fos.write(101);

//        void write​(byte[] b):将 b.length字节从指定的字节数组写入此文件输出流
//        byte[] bys = 97, 98, 99, 100, 101;
        //byte[] getBytes​():返回字符串对应的字节数组
        byte[] bys = "abcde".getBytes();
//        fos.write(bys);

        //void write​(byte[] b, int off, int len):将 len字节从指定的字节数组开始,从偏移量off开始写入此文件输出流
//        fos.write(bys,0,bys.length);
        fos.write(bys,1,3);

        //释放资源
        fos.close();
  • ③. 字节流遇到的两个小问题
  1. 如何实现换行? window:/r/n
  2. 如何实现追加?在FileOutputStream( )构造方法的第二个参数中设置为true
        //创建字节输出流对象
//        FileOutputStream fos = new FileOutputStream("myByteStream\\\\fos.txt");
        FileOutputStream fos = new FileOutputStream("myByteStream\\\\fos.txt",true);

        //写数据
        for (int i = 0; i < 10; i++) 
            fos.write("hello".getBytes());
            fos.write("\\r\\n".getBytes());
        
        //释放资源
        fos.close();
    

  • ④. 小数组文件的复制(重点掌握)
    //定义小数组的标准格式 掌握
    @Test
    public void fun7() throws IOException 
        //定义小数组的标准格式
        //创建输入流对象
        FileInputStream fis=new FileInputStream("xiaozhi.txt");
        //创建输出流对象
        FileOutputStream fos=new FileOutputStream("copyxiaozhi.txt");
        //数组一般是定义1024的整数倍等
        //byte[]arr=new byte[1024*8];
        byte[]arr=new byte[1024];
        int len;
        //如果忘记加arr,返回就不是读取的字节个数,而是字节的码表值
        while((len=fis.read(arr))!=-1)
            //len表示读取到的真实长度
            fos.write(arr,0,len);
            //读取到的数组的长度
            // fos.write(arr,0,arr);
           
        
        fis.close();
        fos.close();
    

④. 字符输入流 - FileReader

  • ①. FileReader构造器
  1. FileReader​(File file):创建一个新的FileReader ,给出File读取
  2. FileReader​(String fileName):创建一个新的 FileReader,给定要读取的文件的名称

  • ②. 方法(继承了父类的读的方法)
  1. int read():读取得字符,如果已经达到末尾,则返回-1
  2. int read(char[ ]ch):写一个字符数组
public class FileReaderWriterTest 
    public static void main(String[] args)

        FileReader fr=null;
        try
            // 将study_java_function\\a.txt文件内容入程序中,并输出控制台
            // a.txt 文件提前写入abcd
            File file=new File("study_java_function\\\\a.txt");
            fr=new FileReader(file);
            // int read():读取得字符,如果已经达到末尾,则返回 -1
            //(1). 方式一
//        int data=fr.read();
//        while(data!=-1)
//            // abcd
//            System.out.print((char)data);
//            data=fr.read();
//        
            // (2). 方式二:语法上针对方式一的修改
            int data;
            while ((data=fr.read())!=-1)
                System.out.print((char)data);
            
        catch (IOException e)
            e.printStackTrace();
        finally 
            // 流的关闭问题
            try 
                if(fr!=null)fr.close();
             catch (IOException e) 
                e.printStackTrace();
            
        
    

@SuppressWarnings("all")
public class FileReaderWriterTest 
    public static void main(String[] args)

        FileReader fr=null;
        try
            // a.txt 文件有abcd1
            fr=new FileReader(new File("study_java_function\\\\a.txt"));

            // 读入操作
            // read(char[]cbuf):返回每次返回cbug数组中的字符个数,如果达到文件末尾,返回-1
            char[]cbuf=new char[2];
            int len;
            while ((len=fr.read(cbuf))!=-1)
                // 错误的写法
//                for (int i = 0; i < cbuf.length ; i++) 
                      // 会输出abcd1d
//                    System.out.print((char)cbuf[i]);
//                
                // 正确的写法
                for (int i = 0; i < len; i++) 
                    System.out.print((char)cbuf[i]);
                
                // 方式二
//                String str=new String(cbuf,0,len);
//                System.out.print(str);
            
        catch (IOException e)
            e.printStackTrace();
        finally 
            // 流的关闭问题
            try 
                if(fr!=null)fr.close();
             catch (IOException e) 
                e.printStackTrace();
            
        
    

⑤. 字符输出流 - FileWriter

  • ①. FileWriter构造器
  1. FileWriter​(String fileName):构造一个给定文件名的FileWriter对象。
  2. FileWriter​(File file):给一个File对象构造一个FileWriter对象
  • ②. FileWriter常用方法
public class FileReaderWriterTest 
    public static void main(String[] args)
        FileWriter fr=null;
        try
            // FileWriter(file,false):默认fasle,表示覆盖
            fr=new FileWriter(new File("study_java_function\\\\b.txt"),false);
            // true表示追加 FileWriter(file,true):不会对原有文件覆盖,而是在原有文件上追加内容
            //fr=new FileWriter(new File("study_java_function\\\\b.txt"),false);
            // 覆盖
            fr.write("I hava a dream\\n");
            fr.write("you need to have a dream");
        catch (IOException e)
            e.printStackTrace();
        finally 
            // 流的关闭问题
            try 
                if(fr!=null)fr.close();
             catch (IOException e) 
                e.printStackTrace();
            
        
    

  • ③. 使用FileReader和FileWriter实现文本文件的复制
    private static final String FILEDESC  ="study_java_function\\\\a.txt";
    public static void main(String[] args)
        FileReader fr=null;
        FileWriter fw=null;
        try
            fr=new FileReader(FILEDESC);
            fw=new FileWriter("study_java_function\\\\d.txt");

            char[]cbuf=new char[2];
            int len;
            while((len=fr.read(cbuf))!=-1)
                // 每次读取几个就写入几个字符
                fw.write(cbuf,0,len);
            
        catch (IOException e)
            e.printStackTrace();
        finally 
            // 流的关闭问题
            try 
                if(fr!=null)fr.close();
                if(fw!=null)fw.close();
             catch (IOException e) 
                e.printStackTrace();
            
        
    
  • ④. 什么情况下使用字符流
  1. 字符流可以拷贝文本文件,但不推荐使用,因为读取时把会字节转为字符,写出时还要把字符转回字节
  2. 程序需要读取一段文本,或者需要写出一段文本的时候可以使用字符流
  3. 读取的时候就按照字符的大小读取的,不会出现半个中文。写出的时候可以直接将字符串写出,不用转换为字节数组

⑥. 字节缓冲流 - Buffered

  • ①. 为什么构造方法需要的是字节流,而不是具体的文件或者路径呢?
    字节缓冲流仅仅提供缓冲区,而真正的读写数据还得依靠基本的字节流对象进行操作

  • ②. 缓冲原理:BufferedInputStream内置了一个缓冲区(数组),从BufferedInputStream中读取一个字时,BufferedInputStream会一次性从文件中读取8192个,存在缓冲区,返回给程序一个。程序再次读取时,就不用找文件了,直接从缓冲区读取,直到缓冲区中所有的都被使用过,才重新从文件中读取8192个

  • ③. 构造函数BufferedInputStream​(InputStream in):创建一个BufferedInputStream并保存其参数,输入流in供以后使用

  • ④. 使用缓冲流实现复制功能

public class BufferTest 
    private static final String FILEDESC  ="study_java_function\\\\IO流.pdf";
    public static void main(String[] args) 
        BufferedInputStream bfis=null;
        BufferedOutputStream bfos=null;
        FileInputStream fis=null;
        FileOutputStream fos=null;
        try
            fis = new FileInputStream(new File(FILEDESC));
            fos = new FileOutputStream("study_java_function\\\\IO流1.pdf");
            // 造缓冲流
            bfis=new BufferedInputStream(fis);
            bfos=new BufferedOutputStream(fos);

            // 复制
            byte[]byteArray=new byte[1024];
            int len;
            while((len=bfis.read(byteArray))!=-1)
                bfos.write(byteArray,0,len);
            
        catch (IOException e)
            e.printStackTrace();
        finally 
            try 
                // 资源关闭
                // 1. 先关闭外层的流,再关闭内层的流
//                if(bfis!=null)bfis.close();
//                if(bfos!=null)bfos.close();
//
//                if(fis!=null)fis.close();
//                if(fos!=null)fos.close();
                // 2. 关闭外层的流,底层会自动将内层帮我们自动关闭
                if(bfis!=null)bfis.close();
                if(bfos!=null)bfos.close();
            catch (IOException e)
                e.printStackTrace();
            
        
    

  • ⑤. 字符缓冲流特有功能
  1. BufferedReader :String readLine():方法可以读取一行字符(不包含换行符号),如果到达了流的结尾它会返回null
  2. BufferedWriter :void newLine():可以输出一个跨平台的换行符号 “\\r\\n”
  3. newLine()和 \\r\\n 的区别
    a. newLine()可以在任意的系统上
    b. \\r\\n 只能在window系统上
   BufferedReader br=new BufferedReader(new FileReader("hello.txt"));
   BufferedWriter bw=new BufferedWriter(new FileWriter("AAA.txt"));

    String len;
    while((len=br.readLine())!=null)
        bw.write(len);
        //写出回车换行符
        bw.newLine();
        //bw.write("\\r\\n");
        // bw.flush();
    
    br.close();
    bw.close();

⑦. 掌握 - 相关流习题操作

  • ①. 集合到文件的案列
/*
    需求:
        把ArrayList集合中的字符串数据写入到文本文件。要求:每一个字符串元素作为文件中的一行数据

    思路:
        1:创建ArrayList集合
        2:往集合中存储字符串元素
        3:创建字符缓冲输出流对象
        4:遍历集合,得到每一个字符串数据
        5:调用字符缓冲输出流对象的方法写数据
        6:释放资源
 */
public class ArrayListToTxtDemo 
    public static void main(String[] args) throws IOException 
        //创建ArrayList集合
        ArrayList<String> array = new ArrayList<String>();

        //往集合中存储字符串元素
        array.add("hello");
        array.add("world");
        array.add("java");

        //创建字符缓冲输出流对象
        BufferedWriter bw = new BufferedWriter(new FileWriter("myCharStream\\\\array.txt"));

        //遍历集合,得到每一个字符串数据
        for(String s : array) 
            //调用字符缓冲输出流对象的方法写数据
            bw.write(s);
            bw.newLine();
            bw.flush();
        

        //释放资源
        bw.close();
    


  • ②. 文件到集合的案列
/*
    需求:
        把文本文件中的数据读取到集合中,并遍历集合。要求:文件中每一行数据是一个集合元素

    思路:
        1:创建字符缓冲输入流对象
        2:创建ArrayList集合对象
        3:调用字符缓冲输入流对象的方法读数据
        4:把读取到的字符串数据存储到集合中
        5:释放资源
        6:遍历集合
 */
public class TxtToArrayListDemo 
    public static void main(String[] args) throws IOException 
        //创建字符缓冲输入流对象
        BufferedReader br = new BufferedReader(new FileReader("myCharStream\\\\array.txt"));

        //创建ArrayList集合对象
        ArrayList<String> array = new ArrayList<String>();

        //调用字符缓冲输入流对象的方法读数据
        String line;
        while ((line=br.readLine())!=null) 
            //把读取到的字符串数据存储到集合中
   

以上是关于IO流01_字节字符流缓冲流标准输入输出流打印流的主要内容,如果未能解决你的问题,请参考以下文章

Java IO流 - 缓冲流的详细使用介绍

Java IO流 - 缓冲流的详细使用介绍

J06-Java IO流总结六 《 BufferedReader和BufferedWriter 》

java _io_字节缓冲流(装饰器)输入输出

缓冲流

JavaSE基础九----<IO流 >流的体系和分类,字节流,字节缓冲流