一篇文章带你深入了解javaIO基础

2022-07-22,,,

目录
  • 一.认识io
    • 1.io的分类
    • 2.io的方式
    • 3.io读写的方式
    • 4.io的特性
    • 3.文件操作的api使用
  • 三.io流

    一.认识io

    1.io的分类

    (1)bio:同步阻塞io

    (2)nio:同步非阻塞io

    (3)aio:异步阻塞io

    注意: 这里主要介绍bio

    2.io的方式

    io本质就是对数据的操作

    (1)网络io

    (2)本地io

    3.io读写的方式

    4.io的特性

    (1)本质上属于数据传输

    (2)涉及两个设备间的传输方向(一般,自己写java程序的时候,只关注自己程序的一方)

    (3)数据流

    (4)java进程的io操作,对进程的影响:

    • 1.阻塞io 会导致进程在运行态和阻塞态之间转变,由操作系统完成后序的io操作
    • 2.java进程,在内核态和用户态之间切换:性能会收到影响(下降)

    (5)io缓冲流

    不使用缓冲流:java程序每次都从主机内存读写数据,每次都直接读取数据/发送数据。write()/read()

    使用/不使用缓冲区的区别:

    例如:循环10000次,每次write1个字节数据到本地文件

    不使用缓冲区:每次循环都是io操作,都涉及进程状态由运行态变为阻塞态,由用户态变为内核态(10000次影响)

    使用缓冲区:每次write复制数据到缓冲区,flush才算io操作(一定要记得)(一次影响)性能更好

    二.文件操作

    1.文件的构成

    (1)文件的头信息(metadata)

    (2)文件的内容

    注意: java.io.file 不是对文件的内容操作,知识对文件本身或者头信息操作

    2.文件的创建

    new操作时的注意事项:

    • 1.既可以指定文件,也可以指定文件夹
    • 2.通过路径创建file:可以使用绝对路径/相对路径
    • 3.不管路径上是否存在这个文件/文件夹,java都可以创建得到一个file对象(但是对这个file操作时,可能会抛出异常)

    3.文件操作的api使用

    文件操作示例:遍历某个目录下,所有的子文件/子文件夹

      public static void main(string[] args) {
            file file=new file("c:\\users\\26905\\desktop\\javacode");
            list<file> list=listdir(file);
    //        for (int i = 0; i <list.size() ; i++) {
    //            system.out.println(list.get(i));
    //        }
            //jdk1.8集合框架使用stream操作,可以使用lambda表达式打印
            list.stream().foreach(system.out::println);
        }
    

    方法一: 效率不高

    public static list<file> listdir(file dir){
            list<file> list=new arraylist<>();
            if(dir.isfile()){
                list.add(dir);//效率不太好的地方,如果是文件,返回的list只存放一个元素
            }else {
                file[] children=dir.listfiles();
                for(file file:children){
                    list<file> files=listdir(file);
                    list.addall(files);
                }
            }
            return list;
        }
    

    方法二: 效率较高

     public static list<file>  listdir2(file dir){
            list<file> list=new arraylist<>();
            if(dir.isdirectory()){
                //获取目录下一级的子文件和子文件夹
                file[] children=dir.listfiles();
                if(children!=null){
                    for(file file:children){
                        if(file.isdirectory()){
                            //如果子文件还是文件夹,递归调用
                            list.addall(listdir2(file));
                        }else{
                            list.add(file);
                        }
                    }
                }
            }
            return list;
        }
    

    三.io流

    1.流的分类

    2.流的创建

    3.流的使用

    <1>输入流

    import java.io.*;
    public class  fileinput {
        /**
         * 字节文件:c:\users\26905\desktop\画图笔记\javaweb\json和ajax简单介绍.png
         * 字符文件:c:\users\26905\desktop\论文,ppt,作业,笔记,图片等\java笔记.txt
         * @param args
         */
        public static void main(string[] args) throws ioexception {
            //图片文件,以二进制的方式操作
            file file1=new file("c:\\users\\26905\\desktop\\画图笔记\\javaweb\\json和ajax简单介绍");
            file file =new file("c:\\users\\26905\\desktop\\论文,ppt,作业,笔记,图片等\\比特草稿本.txt");
    
            //1.文件输入字节流
            fileinputstream fis=new fileinputstream(file);
            //不知道文件有多 大,先定义一个一定大小的字节数组,然后不停读入,每次刷新以下就好
            byte[] bytes=new byte[1024*8];
            //输入流读取的固定写法:读取到一个字节/字符数组,定义read的返回值变量,while
            int len=0;
            //len表示读入字节的长度
            //如果不等于-1,说明读取未结束
            while ((len=fis.read(bytes)) !=-1){
                //读取到的长度,数组可能读满,也可能没有读满
                //当次读取,一般使用数组[0,len]表示读取内容
                //字节数组转字符串
                string str=new string(bytes,0,len);
               // system.out.println(str);
            }
            //一般来说,输入输出流使用完,一定要关闭,关闭的关系是反向关系
            //例如:创建的时候是从里往外创建,则关闭的时候就是从外往内关闭
            fis.close();
    
            //2.文件的字符输入流
            filereader fr=new filereader(file);
            char []chars=new char[1024];
            int lenfr=0;
            while ((lenfr=fr.read(chars))!=-1){
                 string strfr=new string(chars,0,lenfr);
                //system.out.println(strfr);
            }
            fr.close();
    
            //3.缓冲流:缓冲字节输入,缓冲字符输入
            fileinputstream fis=new fileinputstream(file);//文件字节输入流
            //字节流转字符流一定要经过字节字符转换流来转换,并且还可以指定编码
            inputstreamreader isr=new inputstreamreader(fis);
            //缓冲流
            bufferedreader br=new bufferedreader(isr);
            string str;
            //读取,当字符串为空时,结束
            while ((str=br.readline()) !=null){
                system.out.println(str);
            }
            br.close();
            isr.close();
            fis.close();
        }
    }
    

    <2>输出流

    import java.io.file;
    import java.io.fileoutputstream;
    import java.io.ioexception;
    import java.io.printwriter;
    public class fileoutput {
        public static void main(string[] args) throws ioexception {
            /**
             * d:\java代码\1.txt
             */
            //路径上没有该文件,new file不会报错,但是在操作输出流会抛出filenotfoundexception
            file file2=new file("d:\\java代码\\1.txt");
            //把a-z换行输出到某个文件,需要考虑文件是否存在的问题
            if(!file2.exists()){
                file2.createnewfile();
            }
            //new filewriter()  文件的不带缓冲的字符输出
            //new filewriter()  文件的不带缓冲的字节输出
            //new bufferedwriter() 带缓冲的字符输出
            //new printwriter()    打印输出流
    
            //缓冲的字符输出
    //        bufferedwriter bw=new bufferedwriter(new filewriter(file2));
    //        bw.write("\n");
    
            //打印输出流
            //printwriter pw=new printwriter(new filewriter(file));
            printwriter pw =new printwriter(new fileoutputstream(file2));
            //快速打印a-z
            for (int i = 'a'; i <='z' ; i++) {
                pw.println((char)i);
            }
            pw.flush();
        }
    }
    

    <3>实例:文件的复制

    import java.io.file;
    import java.io.fileinputstream;
    import java.io.fileoutputstream;
    import java.io.ioexception;
    public class filecopy {
        public static void main(string[] args) throws ioexception {
            //文件复制
            file input=new file("d:\\java代码\\1.txt");
            file output=new file("d:\\java代码\\2.txt");
            if(!output.exists()){
                output.createnewfile();
            }
            //定义输入输出流
            //输入流
            fileinputstream fis=new fileinputstream(input);
            // 输出流
            fileoutputstream fos=new fileoutputstream(output);
            byte[]bytes=new byte[1024*8];
            int len;
            while ((len=fis.read(bytes))!=-1){//每次从输入流读取到byte[]的内容,直接输出到某个文件,就是复制
                //bytes可能没存满,需要指定长度
                fos.write(bytes,0,len);
            }
            fis.close();
            fos.close();
        }
    }
    

    总结

    本篇文章就到这里了,希望能给你带来帮助,也希望您能够多多关注的更多内容!

    《一篇文章带你深入了解javaIO基础.doc》

    下载本文的Word格式文档,以方便收藏与打印。