IO

File

  • 我们要想实现IO的操作,就必须知道硬盘上文件的表现形式,而Java就提供了一个类供我们使用:File
  • File:文件和目录(文件夹)路径名的抽象表现形式
  • 构造方法:
    • File(File parent, String child)
      • 从父抽象路径名和子路径名字符串创建新的 File实例。
    • File(String pathname)
      • 通过将给定的路径名字符串转换为抽象路径名来创建新的 File实例。
    • File(String parent, String child)
      • 从父路径名字符串和子路径名字符串创建新的 File实例。
public class FileDemo {
    public static void main(String[] args) {
        //File(String pathname) 根据一个路径得到File对象
        //F:\demo\a.txt 封装成一个File对象
        File file = new File("F:\\demo\\a.txt");
        System.out.println(file);

        //File(String parent, String child) 根据一个目录和一个子文件/目录得到File对象
        File file1 = new File("F:\\demo", "a.txt");
        System.out.println(file1);

        //File(File parent, String child) 根据一个父File对象和一个子文件/目录得到File对象
        File file2 = new File("F:\\demo");
        File file3 = new File(file2, "a.txt");
        System.out.println(file3);

    }
}
  • 创建功能
    • public boolean createNewFile()
    • public boolean mkdir()
    • public boolean mkdirs()
public class FileDemo2 {
    public static void main(String[] args) throws IOException {
        //需求:我想在f盘下面创建一个文件夹demo2
//        File file = new File("F:\\demo2");
        //public boolean mkdir() 创建文件夹,如果已经存在这样的文件夹,就不创建了,返回false
//        System.out.println(file.mkdir());


        //需求:我想在f盘下面demo2下面创建一个文件b.txt
        //public boolean createNewFile()
        //创建文件,如果存在这样的文件,就不创建
//        File file1 = new File("F:\\demo2\\b.txt");
//        System.out.println(file1.createNewFile());

        //public boolean mkdirs()
        //创建多级目录,多级文件夹
//        File file = new File("F:\\demo2\\demo3\\demo4");
//        System.out.println(file.mkdirs());


        //java.io.IOException: 系统找不到指定的路径。
        //注意:要想在某个目录下创建文件,该目录必须存在
//        File file1 = new File("F:\\demo3\\b.txt");
//        System.out.println(file1.createNewFile());

        //注意:搞清楚你是想创建文件还是文件夹,骑白马的不一定是王子,还有可能是唐僧
//        File file1 = new File("F:\\demo3\\b.txt");
//        System.out.println(file1.mkdirs());
    }
}
  • 删除功能
  • public boolean delete()
public class FileDemo3 {
    public static void main(String[] args) throws IOException {
        //创建File对象
//        File file = new File("F:\\a.txt");
//        System.out.println(file.createNewFile());

        //在当前项目的根目录上创建一个文件
//        File file1 = new File("a.txt");
//        System.out.println(file1.createNewFile());

        //在当前项目的根目录上创建多级文件夹
//        File file2 = new File("aaa\\bbb\\ccc");
//        System.out.println(file2.mkdirs());

        //public boolean delete()
//        File file3 = new File("a.txt");
//        System.out.println(file3.delete());

        //删除ccc这个文件夹
//        File file4 = new File("aaa\\bbb\\ccc");
//        System.out.println(file4.delete());

        //删除aaa这个文件夹
//        File file5 = new File("aaa");
        //则目录必须为空才能删除
//        System.out.println(file5.delete());

//        File file6 = new File("aaa\\bbb");
//        System.out.println(file6.delete());
        File file7 = new File("aaa");
        System.out.println(file7.delete());

    }
}
  • 重命名功能
    • public boolean renameTo(File dest)
public class FileDemo4 {
    public static void main(String[] args) throws IOException {
        //创建一个文件对象
        File file = new File("冯提莫.jpg");
//        System.out.println(file.createNewFile());
        //现在我想重名为 可爱屁.jpg
        File file1 = new File("可爱屁.jpg");
        System.out.println(file.renameTo(file1));
    }
}public class FileDemo4 {
    public static void main(String[] args) throws IOException {
        //创建一个文件对象
        File file = new File("冯提莫.jpg");
//        System.out.println(file.createNewFile());
        //现在我想重名为 可爱屁.jpg
        File file1 = new File("可爱屁.jpg");
        System.out.println(file.renameTo(file1));
    }
}
  • 判断功能
    •  public boolean isDirectory()
    •  public boolean isFile()
    •  public boolean exists()
    •  public boolean canRead()
    •  public boolean canWrite()
    •  public boolean isHidden()
public class FileDemo5 {
    public static void main(String[] args) throws IOException {

        //创建一个File文件对象
        File file = new File("a.txt");
//        System.out.println(file.createNewFile());

        //public boolean isDirectory() 判断是否是文件夹
        System.out.println(file.isDirectory());
        //public boolean isFile() 判断是否是文件
        System.out.println(file.isFile());
        //public boolean exists() 判断File对象是否存在
        System.out.println(file.exists());
        //public boolean canRead() 判断是否可读
        System.out.println(file.canRead());
        //public boolean canWrite() 判断是否可写
        System.out.println(file.canWrite());
        //public boolean isHidden() 判断是否隐藏
        System.out.println(file.isHidden());
    }
}
  • 基本获取功能
    •  public String getAbsolutePath()
    •  public String getPath()
    •  public String getName()
    •  public long length()
    •  public long lastModified()
public class FileDemo6 {
    public static void main(String[] args) throws IOException {
        File file = new File("demo\\test.txt");
//        System.out.println(file.mkdir());
//        System.out.println(file.createNewFile());

        //public String getAbsolutePath()
        //获取绝对路径,或者说是完整路径
        System.out.println(file.getAbsolutePath());

        //public String getPath()
        //获取相对路径
        System.out.println(file.getPath());

        //public String getName()
        //获取名称
        System.out.println(file.getName());

        //public long length()
        //获取的长度是字节数
        File file1 = new File("C:\\Users\\xiaohu\\Desktop\\HashSet中add方法源码.java");
        System.out.println(file1.length());

        //public long lastModified()
        //获取到的是时间戳,精确到毫秒
        System.out.println(file.lastModified());

        //1628929592356
        //时间戳与日期的转换
        Date date = new Date(1628929592356L);
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        String s = sdf.format(date);
        System.out.println(s);
    }
}
  • 高级获取功能
    • public String[] list()
    • public File[] listFiles()
public class FileDemo7 {
    public static void main(String[] args) {
        File file = new File("E:\\数加科技\\十二期");

        //public String[] list()
        //获取指定目录下的所有文件或者文件夹的名称数组
//        String[] list = file.list();
//        for (String s :list) {
//            System.out.println(s);
//        }

        System.out.println("-----------");

        //public File[] listFiles()
        //获取指定目录下的所有文件或者文件夹的File数组
        File[] files = file.listFiles();
        for (File f:files) {
            System.out.println(f.getName());
        }
    }
}
  • 练习
  •  判断E盘E:\数加科技\十二期目录下是否有后缀名为.jpg的文件,如果有,就输出此文件名称
  •  分析:
    • 获取到E:\数加科技\十二期的目录
    • 获取该目录下所有的文件和文件夹的File数组
    • 遍历该File数组,得到每一个File对象,然后判断是否是文件
    • 判断是否是文件
      • 是:继续判断是否是以.jpg后缀
        • 是:输出该文件名称
        • 否:不管他
      •  否:不管他
public class FileDemo8 {
    public static void main(String[] args) {
        //创建File对象
        File file = new File("E:\\数加科技\\十二期");

        //获取该目录下所有的文件和文件夹的File数组
        File[] files = file.listFiles();

        //定义一个集合存储名字
        ArrayList<String> strings = new ArrayList<String>();

        int count =0;

        //遍历该File数组,得到每一个File对象,然后判断是否是文件
        for (File f :files) {
            //判断是否是文件
            if(f.isFile()){
                //继续判断是否是以.jpg后缀
                if(f.getName().endsWith(".jpg")){
                    count++;
                    //输出该文件名称
                    strings.add(f.getName());
                }
            }
        }

        System.out.println("该目录下共有"+count+"个以.jpg后缀的文件");
        System.out.println("分别是:");
        for (String s:strings) {
            System.out.println(s);
        }
    }
}

 

递归

  • 递归的概述:以编程的角度来看,递归指的是方法定义中调用方法本身的现象
  • 递归解决问题的思路:
    • 把一个复杂的问题层层转化称为一个与原问题相似的规模较小的问题来求解
    • 递归策略只需要少量的程序就可描述出解题过程所需要的多次重复计算
  • 递归问题要找到两个内容
    • 递归出口:否则会出现内存溢出
    • 递归规则:与原问题相似的规模较小的问题
package Translation;
/*
        递归的概述:以编程的角度来看,递归指的是方法定义中调用方法本身的现象
*/
public class TranslationDemo {
    public static void main(String[] args) {
        //求第20个月兔子的对数
        //每个月兔子的对数:1,1,2,3,5,8,....
        int[] arr = new int[20];
        arr[0] = 1;
        arr[1] = 1;

        for (int i = 2; i <arr.length ; i++) {
            arr[i] = arr[i-1]+ arr[i-2];
        }
        System.out.println(arr[19]);
        System.out.println(f(20));
    }

    /*
        递归解决问题 首先就是定义一个方法
            定义一个方法f(n),表示第n个月的兔子对数
            那么,第n-1个月的兔子对数该如何表示呢?f(n-1)
            那么,第n-2个月的兔子对数该如何表示呢?f(n-2)
    */

    public  static int f(int n) {
        if (n == 1 || n == 2) {
            return 1;
        } else {
            return f(n - 1) + f(n - 2);  //StackOverflowError   当堆栈溢出发生时抛出一个应用程序递归太深。
        }
    }
}

练习:

递归求阶乘

package Translation;
/*
            需求:用递归求5的阶乘,并把结果在控制台输出
            分析:
                1.阶乘:一个正整数的阶乘是所有小于及等于该数的正整数的积,自然数n的阶乘写作n!
                       5! = 5*4*3*2*!
                2.递归出口:1! = 1
                3.递归规则:n ! = n*(n-1)!
                       5! = 5*4!


*/
public class TranslationDemo2 {

    //定义一个方法
    public static int Tr(int i ){
        if(i == 1){
            return 1;
        }
        else{
            return i*Tr(i-1);
        }
    }

    public static void main(String[] args) {
        System.out.println(Tr(5));
    }
}

内存图

练习2:

遍历目录

需求:给定一个路径(D:\兰智视频\JAVA\第二十天),请通过递归完成遍历该目录下的所有内容,并把所有文件的绝对路径输出在控制台

思路:
1.根据给定的路径创建一个File对象
2.定义一个方法,用于获取给定目录下的所有内容,参数为第一步创建的File对象
3.获取给定的File目录下所有的文件或者目录的File数组
4.遍历该File数组,得到每一个File对象
5.判断该File对象是否是空目录
是:递归调用
不是:获取绝对路径输出在控制台
6.调用方法
package Translation;

import java.io.File;

/*
           需求:给定一个路径(D:\兰智视频\JAVA\第二十天),请通过递归完成遍历该目录下的所有内容,并把所有文件的绝对路径输出在控制台

           思路:
                1.根据给定的路径创建一个File对象
                2.定义一个方法,用于获取给定目录下的所有内容,参数为第一步创建的File对象
                3.获取给定的File目录下所有的文件或者目录的File数组
                4.遍历该File数组,得到每一个File对象
                5.判断该File对象是否是空目录
                    是:递归调用
                    不是:获取绝对路径输出在控制台
                6.调用方法
*/
public class TranslationDemo3 {
    public static void main(String[] args) {
        //创建File对象
        File srcfile = new File("D:\\兰智视频\\JAVA\\第二十天");

        //调用方法
        getAllfilePath(srcfile);

    }

    public static void getAllfilePath(File srcfile){
        //获取给定的file目录下所有的文件或者目录的File数组
        File[] fileArray = srcfile.listFiles();
        //遍历该File数组,得到每一个File对象
        if (fileArray != null){
            for (File file : fileArray){
                //判断该File对象是否是目录
                if (file.isDirectory()){
                    //是,递归调用
                    getAllfilePath(file);
                }
                else {
                    System.out.println(file.getAbsolutePath());
                }
            }
        }
    }
}

 

字节流

  • IO流概述和分类
    • IO流概述
      • IO:输入/输出(input/Output)
      • 流:是一种抽象概念,是对数据传输的总数,也就是说数据在设备间的传输称为流,流的本质是数据传输
      • IO流就是用来处理设备间数据传输问题的
        • 常见的应用:文件复制;文件上传;文件下载

 

  • IO流分类:
    • 按照数据的流向
      • 输入流:读数据
      • 输出流:写数据
  • 按照数据类型来分
    • 字节流
      • 字节输入流;字节输出流
    • 字符流
      • 字符输入流;字符输出流
  • 一般来说,我们说IO流的分类是按照数据类型来分的·
  • 如果数据通过Windows自带的记事本软件打开,我们还可以读懂里面的内容,就使用字符流,否则使用字节流。如果你不知道该使用哪种类型的流,就使用字节流

 

 

字节流写数据

  • 字节流抽象基类
    • InputStream: 这个抽象类是表示字节输入流的所有类的超类
    • OutputStream: 这个抽象类是表示字节输出流的所有类的超类
    • 子类名特点:子类名称都是以父类名作为子类名的后缀
  • FileOutputStream:文件输出流用于将数据写入File
    • FileOutputStream(String name) :创建文件输出流以指定的名称写入文件
  • 使用字节输出流写数据的步骤
    • 创建字节输出流对象(调用系统功能创建了文件,创建了字节输出流对象,让字节输出流对象指向文件)
    • 调用字节输出流对象写数据方法
    • 释放资源(关闭此文件输出流并释放与此流相关联的任何系统资源)
package Translation;

import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

/*
            FileOutputStream:文件输出流用于将数据写入File
                    FileOutputStream(String name) :创建文件输出流以指定的名称写入文件
*/
public class TranslationDemo4 {
    public static void main(String[] args) throws IOException {
        //创建字节输出流对象
        FileOutputStream fas = new FileOutputStream("fax.txt");
        /*
               做了三件事情
                    A :调用系统功能创建了文件
                    B :创建了字节输出流对象
                    C :让字节输出流对象指向创建好的文件
        */

        //void write (int b);将指定的字节写入此文件输出流
        fas.write(97);
//        fas.write(57);
//        fas.write(55);

        //最后都要释放资源
        //void close (): 关闭此文件输出流并释放与此流相关联的任何系统资源

        fas.close();
    }
}

 

字节流写数据的3种方式

package Translation;


/*  
                void write(int b)将指定的字节写入此文件输出流。
                void write(byte[] b)将 b.length个字节从指定的字节数组写入此文件输出流。
                void write(byte[] b, int off, int len) 将 len字节从位于偏移量 off的指定字节数组写入此文件输出流。

*/

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

public class TranslationDemo5 {
    public static void main(String[] args) throws IOException {
        //FileOutputStream(String name) 创建文件输出流以指定的名称写入文件
        FileOutputStream fos = new FileOutputStream("fos.txt");
        //new File(name)
//        FileOutputStream fos = new FileOutputStream(new File("fos.txt"));

        //FileOutputStream(File file), 创建文件输出流以写入由指定的File对象表示的文件
//
//        File file = new File("fos.txt");
//        FileOutputStream fos2 = new FileOutputStream(file);
//        FileOutputStream fos2 = new FileOutputStream(new File("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 = "abced".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);
    }
}

 

字节流写数据的两个小问题

  • 字节流写数据如何实现换行?
    • 加换行符
      • window:\r\n
      • linux:\n
      • mac:\r
  • 字节流写数据如何实现追加写入?
    • public FileOutputStream(String name,boolean append)

    • 如果第二个参数是true ,则字节将写入文件的末尾而不是开头。 创建一个新的FileDescriptor对象来表示此文件连接。

package Translation;

import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

/*
            1.字节流写数据如何实现换行?
                  window:\r\n
                  linux:\n
                   mac:\r

            2.字节流写数据如何实现追加写入?
                public FileOutputStream(String name,boolean append)
                如果第二个参数是true ,则字节将写入文件的末尾而不是开头。 创建一个新的FileDescriptor对象来表示此文件连接。
*/

public class TranslationDemo6 {
    public static void main(String[] args) throws IOException {
        FileOutputStream fos = new FileOutputStream("fos.txt",true);
        //写数据
        for (int i = 0; i < 10; i++) {
            fos.write("hello".getBytes());
            fos.write("\n".getBytes());
        }

        //释放资源
        fos.close();
    }
}
字节流写数据加异常处理
  • finally:在异常处理时提供finally块来执行所有清除操作。比如说IO流中的释放资源
  • 特点:被finally控制的语句一定会执行,除非JVM退出

 

 

 

package Translation;

import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

/*
        字节流写数据加入异常处理
*/
public class TranslationDemo7 {
    public static void main(String[] args) throws FileNotFoundException {
//        try {
//            FileOutputStream fos = new FileOutputStream("fos.txt");
//            fos.write("hello".getBytes());
//            fos.close();
//        }catch (IOException e){
//            e.printStackTrace();
//        }

//         加入finally来实现释放资源
        FileOutputStream fos  = null;
        try {
//            fos = new FileOutputStream("Z:\\fos.txt");
            fos = new FileOutputStream("fos.txt");
            fos.write("hello".getBytes());
        }catch (IOException e){
            e.printStackTrace();
        }finally {
            if (fos != null) {
                try {
                    fos.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
    }
}

 

 

 字节流读数据

  • 需求:把文件fos.txt中的内容读取出来在控制台输出
  • FileInputStream(String name)通过打开与实际文件的连接来创建一个 FileInputStream ,该文件由文件系统中的路径名 name命名。
  • 使用字节输入流读数据的步骤
    • 创建字节输入流对象
    • 调用字节输入流对象的读数据方法
    • 释放资源
package IO;

import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

/*需求:把文件fos.txt中的内容读取出来在控制台输出
        FileInputStream(String name)通过打开与实际文件的连接来创建一个 FileInputStream ,该文件由文件系统中的路径名 name命名。
        使用字节输入流读数据的步骤
            创建字节输入流对象
            调用字节输入流对象的读数据方法
            释放资源*/
public class FileInputStreamDemo1 {
    public static void main(String[] args) throws IOException {
        //创建字节输入流对象
        // FileInputStream(String name)
        FileInputStream  fos = new FileInputStream("fos.txt");

        //调用字节输入流对象的读数据方法
        //int read(): 从该输入流读取一个字节的数据。

//        //第一次读取数据
//        int read = fos.read();
//        System.out.println(read);
//        System.out.println((char)read);
//
//        //第二次读取数据
//        read = fos.read();
//        System.out.println(read);
//        System.out.println((char)read);
//
//        //再多读取两次
//        read = fos.read();
//        System.out.println(read);
//        read = fos.read();
//        System.out.println(read);
//
//        //数据的下一个字节,如果达到文件的末尾, -1 。

//        int by = fos.read();
//        while (by != -1){
//            System.out.print((char)by);
//            by = fos.read();
//        }

        //优化上面的程序
        int by;
        /*
            fos.read(),读数据
            by = fos.read(),把读取到的数据复制给by
            by != -1 判断读取到的数据是否是-1.
        */
        while ((by = fos.read()) != -1){
            System.out.print((char)by);
        }

        //释放资源
        fos.close();
        
    }
}

案例

  • 需求:把“fos.txt”文件复制到模块目录下的"java.txt"文件
  • 分析:
    • 复制文本文件,其实就是把文本文件的内容从一个文件中读取出来(数据源),然后写入到另一个文件中(目的地)
    • 数据源
      • fos.txt----读数据----InputStream----FileInputStream
    • 目的地
      • java.txt----写数据----OutputStream----FileOutputStream
  • 思路:
    • 根据数据源创建字节输入流对象
    • 根据目的地创建字节输出流对象
    • 读写数据,复制文本文件(一次读取一个字节,一次写入一个字节)
    • 释放资源
package IO;

import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

public class FIleDemo2 {
    public static void main(String[] args) throws IOException {
        //根据数据源创建字节输入流对象
        FileInputStream fos = new FileInputStream("fos.txt");

        //根据目的地创建字节输入流对象
        FileOutputStream java = new FileOutputStream("java.txt");

        //读写数据,复制文本文件
        int by;
        while ((by = fos.read())!=-1){
            java.write(by);
        }

        //释放资源
        fos.close();
        java.close();
    }
}

 

 字节流读数据(一次读一数组)

  • 需求:把文件fos.txt中的内容读取出来在控制台输出
  • FileInputStream(String name)通过打开与实际文件的连接来创建一个 FileInputStream ,该文件由文件系统中的路径名 name命名。
  • 使用字节输入流读数据的步骤
    • 创建字节输入流对象
    • 调用字节输入流对象的读数据方法
    • 释放资源
package IO;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;

public class IODemo1 {
    public static void main(String[] args) throws IOException {
        //创建对象
        FileInputStream fos = new FileInputStream("fos.txt");

 /*       //int read(byte[] b)  从该输入流读取最多 b.length个字节的数据为字节数组。
        byte[] by = new byte[5];
        //第一次读取数据
        int read = fos.read(by);
        System.out.println(read);

        //String(byte[] bytes)  通过使用平台的默认字符集解码指定的字节数组来构造新的 String 。
//        System.out.println(new String(by));
        System.out.println(new String(by,0,read));

        //第二次读取数据
        read = fos.read(by);
        System.out.println(read);
//        System.out.println(new String(by));
        System.out.println(new String(by,0,read));

        read = fos.read(by);
        System.out.println(read);
        //String(byte[] bytes, int offset, int length) 通过使用平台的默认字符集解码指定的字节子阵列来构造新的 String 。
        System.out.println(new String(by,0,read));

        //再多读取两次
        read = fos.read(by);
        System.out.println(read);
        read = fos.read(by);
        System.out.println(read);*/
 
        //用循环改进
        byte[] bys = new byte[1024];  //1024及其整数倍
        int len;
        while ((len = fos.read(bys)) != -1 ){
            System.out.println(new String(bys,0,len));
        }
/*
        abcde\r\n
        hello\r\n
        world\r\n
        java\r\n

        第一次abcde
        第二次\r\nhel
        第三次lo\r\nw

        返回的数据为读取的个数
*/
        //释放
        fos.close();
    }
}

案列

  • 复制图片
package IO;

import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

/*
*               需求:
*                    复制图片到模块目录下
*               思路:
*                    1.根据数据源创建字节输入对象
*                    2.根据目的地创建字节输出对象
*                    3.读写数据,复制图片
*                    5.释放资源
*
* */
public class IODemo2 {
    public static void main(String[] args) throws IOException {
        //创建字节输入流对象
        FileInputStream fos = new FileInputStream("D:\\兰智视频\\JAVA\\第二十天\\aa.jpg");

        FileOutputStream  bis = new FileOutputStream("bb.jpg");
        
        byte[] bys = new byte[1024];
        int len ;
        while ((len = fos.read(bys))!= -1){
            bis.write(bys,0,len);
        }
        fos.close();
        bis.close();
    }
}

字节缓冲流

  • public class BufferedOutputStream
    通过设置这样的输出流,应用程序可以向底层输出流写入字节,而不必为写入的每个字节导致底层系统的调用。

  • public class BufferedInputStream
    当创建BufferedInputStream时,将创建一个内部缓冲区数组。 当从流中读取或跳过字节时,内部缓冲区将根据需要从所包含的输入流中重新填充,一次有多个字节。 mark操作会记住输入流中的一点,并且reset操作会导致从最近的mark操作之后读取的所有字节在从包含的输入流中取出新的字节之前重新读取。

  • 构造方法
    • 字节缓冲输出流:BufferedOutputStream(OutputStream out)
    • 字节缓冲输入流:BufferedInputStream(InputStream in)
  • 为什么构造方法需要的是字节流,而不是具体的文件或者路径呢?
    • 字节缓冲流仅仅是提供缓冲区,而真正的读写数据还得依靠基本的字节流对象进行操作
package IO;



import java.io.*;

/*

        字节缓冲输出流:BufferedOutputStream(OutputStream out)
        字节缓冲输入流:BufferedInputStream(InputStream in)

        */
public class IODemo3 {
    public static void main(String[] args) throws IOException {
        //字节缓冲输出流 BufferedOutputStream(OutputStream out)

//        FileOutputStream fos = new FileOutputStream("fos.txt");
//        BufferedOutputStream bos = new BufferedOutputStream(fos);
//
//        BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream("fos.txt"));
//
//        //写数据
//        bos.write("hello\r\n".getBytes());
//        bos.write("world\r\n".getBytes());
//
//        //释放资源
//        bos.close();

        //字节缓冲输入流:BufferedInputStream(InputStream in)
        BufferedInputStream fos = new BufferedInputStream(new FileInputStream("fos.txt"));

        //一次读取一个字节数据
//        int  by;
//        while (((by = fos.read())!= -1)){
//            System.out.println((char)by);
//        }
        
        
        //一次读取一个字节数组
        byte[] by2 = new byte[1024];
        int len;
        while ((len = fos.read(by2))!= -1){
            System.out.println(new String(by2,0,len));
        }
    }
}

 案列

  • 字节流复制视频
package IO;

import java.io.*;

/*
*            需求:
*                复制视频
*            思路:
*                1.基本字节流一次读写一个字节     //共耗时,36501毫秒'
*                2.基本字节流一次读写一个字节数组   //共耗时,51毫秒'
*                3,字节缓冲流一次读写一个字节        //共耗时,213毫秒'
*                4.字节缓冲流一次读写一个字节数组      //共耗时,19毫秒'
*
*
* */
public class IODemo4 {
    public static void main(String[] args) throws IOException {
        //记录开始时间
        long startTime = System.currentTimeMillis();


        //复制视频

        method4();




        //结束时间
        long endTime = System.currentTimeMillis();
        System.out.println("共耗时,"+(endTime - startTime)+"毫秒'");
    }

    //基本字节流一次读写一个字节
    public static void method1() throws IOException {
//        D:\兰智视频\JAVA\第二十天
        FileInputStream fis = new FileInputStream("D:\\兰智视频\\JAVA\\第二十一天\\大数据2.mp4");
        FileOutputStream fos = new FileOutputStream("YS.mp4");

        int by;
        while ((by = fis.read())!= -1){
            fos.write(by);
        }

        fos.close();
        fis.close();
    }

    //基本字节流一次读写一个字节数组

    public static void method2() throws IOException {
//        D:\兰智视频\JAVA\第二十天
        FileInputStream fis = new FileInputStream("D:\\兰智视频\\JAVA\\第二十一天\\大数据2.mp4");
        FileOutputStream fos = new FileOutputStream("YS.mp4");

      byte[] bys = new byte[1024];
      int len;
      while ((len = fis.read(bys))!= -1){
          fos.write(bys,0,len);
      }

        fos.close();
        fis.close();
    }

    //字节缓冲流一次读写一个字节
    public static void method3() throws IOException {
        BufferedInputStream bif = new BufferedInputStream(new FileInputStream("D:\\兰智视频\\JAVA\\第二十一天\\大数据2.mp4"));
        BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream("Ys.mp4"));

        int by;
        while ((by = bif.read())!= -1){
            bos.write(by);
        }
        bos.close();
        bif.close();
    }

    //字节缓冲流一次读写一个字节数组
    public static void method4() throws IOException {
        BufferedInputStream bif = new BufferedInputStream(new FileInputStream("D:\\兰智视频\\JAVA\\第二十一天\\大数据2.mp4"));
        BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream("Ys.mp4"));

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

}

字符流

  • 为什么要出现字符流
    • 一个汉字存储
      • 如果是GBK编码,占用2个字节
      • 如果是UTF-8编码,占用3个字节
    • 由于字节流中文操作不是特别方便,所以java就提供字符流
      • 字符流=字节流+编码表
    • 用字节流复制文本文件时,文本文件也会有中文,但是没有问题,原因是最底层操作会自动进行字节流拼接成中文,如何识别是中文呢?
      • 汉子在存储的时候,无论选择哪种编码存储,第一个字节都是负数。
  • 编码表
    • 基础知识
      • 计算机中储存的信息都是用二进制数表示的;我们在屏幕上看到的英文,汉字等字符是二进制数转换之后的结果
    • 按照某种规则,将字符存储到计算机中,称为编码,反之,将存储在计算机中的二进制数按照某种规则解析显示出来,称为编码。这里强调一下,按照A编码存储,必须按照A编码解析,按照B编码存储,必须按照B编码解析,才会显示正确符号,否则会出现乱码。
      • 字符编码:就是一套自然语言的字符与二进制数之间的对应规则(A,65)
    • 字符集
      • 是一个系统支持的所有字符的集合,包括各国家文字,标点符号,图形符号,数字等。
      • 计算机要准确的存储和识别各种字符集符号,就需要进行字符编码,一套字符集必然至少有一套字符编码,常见的字符集有ASCII字符集,GBXXX字符集,Unicode字符集等。
  • 字符串中的编码解码问题
    • 编码
      • byte[] getBytes(): 使用平台默认的字符集将该String编码为一系列字节,将结果存储到新的字节数组中
      • byre[] getBytes(String charsetName): 使用制定的字符集将该String编码为一系列字节,将结果存储到新的字节数组中
    • 解码
      • String(byte[] bytes): 通过使用平台的默认字符集解码制定的字节数组来构造新的String
      • String(byte[] byte,String charsetName): 通过指定的字符集解码指定的字节数组来构造新的String
package IO;



import java.io.UnsupportedEncodingException;
import java.util.Arrays;

/*编码
        byte[] getBytes(): 使用平台默认的字符集将该String编码为一系列字节,将结果存储到新的字节数组中
        byre[] getBytes(String charsetName): 使用制定的字符集将该String编码为一系列字节,将结果存储到新的字节数组中
        解码
        String(byte[] bytes): 通过使用平台的默认字符集解码制定的字节数组来构造新的String
        String(byte[] byte,String charsetName): 通过指定的字符集解码指定的字节数组来构造新的String*/
public class IODemo6 {
    public static void main(String[] args) throws UnsupportedEncodingException {
        String s = "中国";

//        byte[] getBytes(): 使用平台默认的字符集将该String编码为一系列字节,将结果存储到新的字节数组中
//        byte[] bys = s.getBytes();             //[-28, -72, -83, -27, -101, -67]
//        byre[] getBytes(String charsetName): 使用制定的字符集将该String编码为一系列字节,将结果存储到新的字节数组中
//        byte[] bys = s.getBytes("UTF-8");     [-28, -72, -83, -27, -101, -67]
        byte[] bys = s.getBytes("GBk");      // [-42, -48, -71, -6]

        System.out.println(Arrays.toString(bys));

        //String(byte[] bytes): 通过使用平台的默认字符集解码制定的字节数组来构造新的String
        String ss = new String(bys,"GBK");
        //String(byte[] byte,String charsetName): 通过指定的字符集解码指定的字节数组来构造新的String*/
        System.out.println(ss);
    }
}

 

字符流中的编码解码问题、

  • 字符流抽象基类
    • Reader:字符输入流的抽象类
    • Writer:字符输出流的抽象类
  • 字符流中和编码解码问题相关的两个类
    • InputStreamReader   
      • InputStreamReader是从字节流到字符流的桥:它读取字节,并使用指定的charset将其解码为字符 。 它使用的字符集可以由名称指定,也可以被明确指定,或者可以接受平台的默认字符集。
      • InputStreamReader(InputStream in) 创建一个使用默认字符集的InputStreamReader。
        InputStreamReader(InputStream in, Charset cs) 创建一个使用给定字符集的InputStreamReader。

    • OutputStreamWriter
      • OutputStreamWriter是字符的桥梁流以字节流:向其写入的字符编码成使用指定的字节charset 。 它使用的字符集可以由名称指定,也可以被明确指定,或者可以接受平台的默认字符集。
      •  OutputStreamWriter(OutputStream out) 创建一个使用默认字符编码的OutputStreamWriter。
         OutputStreamWriter(OutputStream out, Charset cs) 创建一个使用给定字符集的OutputStreamWriter。

package IO;

import java.io.*;

/*
        InputStreamReader是从字节流到字符流的桥:它读取字节,并使用指定的charset将其解码为字符 。 它使用的字符集可以由名称指定,也可以被明确指定,或者可以接受平台的默认字符集。

        OutputStreamWriter是字符的桥梁流以字节流:向其写入的字符编码成使用指定的字节charset 。 它使用的字符集可以由名称指定,也可以被明确指定,或者可以接受平台的默认字符集。*/
public class IODemo7 {
    public static void main(String[] args) throws IOException {
//        OutputStreamWriter(OutputStream out) 创建一个使用默认字符编码的OutputStreamWriter。
//        OutputStreamWriter(OutputStream out, Charset cs) 创建一个使用给定字符集的OutputStreamWriter。

//        FileOutputStream fos = new FileOutputStream("fos.txt");
//        OutputStreamWriter osw = new OutputStreamWriter(fos);

//        OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("fos.txt")); //默认的是UTF-8
        OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("fos.txt"),"GBK");
        osw.write("中国");
        osw.close();


//        InputStreamReader(InputStream in) 创建一个使用默认字符集的InputStreamReader。
//        InputStreamReader(InputStream in, Charset cs) 创建一个使用给定字符集的InputStreamReader。

//        InputStreamReader isr = new InputStreamReader(new FileInputStream("fos.txt"));
        InputStreamReader isr = new InputStreamReader(new FileInputStream("fos.txt"),"GBK");

        //一次读取一个数据
        int ch;
        while ((ch = isr.read())!= -1){
            System.out.print((char)ch);
        }

        isr.close();

    }
}

 

字符流写数据的5种方式

 

 

 

package IO;

//          void write(int c) 写一个字符
//          vodi write(char[] cbuf),写入一个字符数组
//          void write(char[] cbuf, int off, int len) 写入字符数组的一部分。
//          void write(String str),写一个字符串
//          void write(String str, int off, int len)写一个字符串的一部分。


import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStreamWriter;

public class IODemo8 {
    public static void main(String[] args) throws IOException {
        OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("fos.txt"));

//        //写入一个字符
//        osw.write(97);
//        //void flush刷新流
//        osw.flush();
//        osw.write(98);
//        osw.flush();
//        osw.write(99);


//       vodi write(char[] cbuf),写入一个字符数组
//        char[] chs = {'a','b','c','d','e'};
//        osw.write(chs);

//        void write(char[] cbuf, int off, int len) 写入字符数组的一部分。
//        char[] chs = {'a','b','c','d','e'};
//        osw.write(chs,0,3);

//        void write(String str),写一个字符串
//        String s = "abcde";
//        osw.write(s);

        //void write(String str, int off, int len)写一个字符串的一部分。
        osw.write("abcde",1,3);

        osw.close();
    }
}

 

 字符流读数据的2种方式

 

 

package IO;
//
//          int read()读一个字符
//
//          int read(char[] cbuf, int offset, int length) 将字符读入数组的一部分。

import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStreamReader;

public class IODemo9 {
    public static void main(String[] args) throws IOException {
        InputStreamReader ios = new InputStreamReader(new FileInputStream("fos.txt"));

        //int read()读一个字符
//        int ch;
//        while ((ch = ios.read())!=-1){
//            System.out.print((char) ch);
//        }

        //int read(char[] cbuf, int offset, int length) 将字符读入数组的一部分。
        char[] chs = new char[1024];
        int len;
        while ((len = ios.read(chs))!=-1){
            System.out.println(new String(chs,0,len));
        }

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

    }
}

案例

  • 复制Java文件
package IO;

import java.io.*;

/*

            复制Java文件

*/
public class IODemo10 {
    public static void main(String[] args) throws IOException {
        //根据数据源创建字符输入流对象
        InputStreamReader isr = new InputStreamReader(new FileInputStream("E:\\IDEJAVA\\student\\src\\IO\\IODemo1.java"));
        //根据目的地创建字符输出流对象
        OutputStreamWriter osw = new OutputStreamWriter(new FileOutputStream("wohu.java"));


        //读写数据,复制文件
        //一次读写一个字符数据
//        int ch;
//        while ((ch=isr.read())!=-1){
//            osw.write(ch);
//        }
        

        //一次读写一个字符数组
        char[] chr = new char[1024];
        int len;
        while ((len =isr.read(chr))!=-1){
            osw.write(chr,0,len);
        }
        //释放对象
        osw.close();
        isr.close();
    }
}

改进版

package IO;

import Test.Fileread;

import java.io.*;

/*
                复制Java文件,改进版
                FileReader
                FileWriter

*/
public class IODemo11 {
    public static void main(String[] args) throws IOException {
        //根据数据源创建字符输入流对象
        FileReader frd = new FileReader("E:\\IDEJAVA\\student\\src\\IO\\IODemo1.java");
        //根据目的地创建字符输出流对象
        FileWriter fw = new FileWriter("wohu.java");

        //读写数据,复制文件
//        int ch;
//        while ((ch = frd.read())!=-1){
//            fw.write(ch);
//        }
        char[] chs = new char[1024];
        int len;
        while ((len = frd.read(chs))!=-1){
            fw.write(chs,0,len);
        }

        //释放文件
        fw.close();
        frd.close();
    }
}

字符缓冲流

  • BufferedReader(Reader in) 
    • 创建使用默认大小的输入缓冲区的缓冲字符输入流。从字符输入流读取文本,缓冲字符,以提供字符,数组和行的高效读取。可以指定缓冲区大小,或者可以使用默认大小。 默认值足够大,可用于大多数用途。 
  • BufferedWriter(Writer out)    
    • 创建使用默认大小的输出缓冲区的缓冲字符输出流。将文本写入字符输出流,缓冲字符,以提供单个字符,数组和字符串的高效写入。可以指定缓冲区大小,或者可以接受默认大小。 默认值足够大,可用于大多数用途。
package IO;



import java.io.*;

/*          BufferedReader(Reader in)
                    创建使用默认大小的输入缓冲区的缓冲字符输入流。从字符输入流读取文本,缓冲字符,以提供字符,数组和行的高效读取。
                    可以指定缓冲区大小,或者可以使用默认大小。
                    默认值足够大,可用于大多数用途。
            BufferedWriter(Writer out)    
                    创建使用默认大小的输出缓冲区的缓冲字符输出流。
                    将文本写入字符输出流,缓冲字符,以提供单个字符,数组和字符串的高效写入。可以指定缓冲区大小,或者可以接受默认大小。
                    默认值足够大,可用于大多数用途*/
public class IODemo12 {
    public static void main(String[] args) throws IOException {
//        FileWriter fw = new FileWriter("wohu.java");
//        BufferedWriter bw = new BufferedWriter(fw);

//        BufferedWriter bf = new BufferedWriter(new FileWriter("wuhu.java"));
//        bf.write("hello");
//        bf.newLine();
//        bf.write("world");
//        bf.newLine();
//        bf.write("java");
//        bf.newLine();
//
//        bf.close();


        BufferedReader bf = new BufferedReader(new FileReader("wuhu.java"));

        char[] chars = new char[1024];
        int len;
        while ((len = bf.read(chars))!=-1){
            System.out.println(new String(chars,0,len));
        }
    }
}

使用字符缓冲流复制Java文件

package IO;

import java.io.*;

/*
*                   字符缓冲流复制JAVA文件
*
*
* */
public class IODemo13 {
    public static void main(String[] args) throws IOException {
        BufferedReader bf = new BufferedReader(new FileReader("wohu.java"));
        BufferedWriter bw = new BufferedWriter(new FileWriter("wuhu.java"));
        
        char[] chs = new char[1024];
        int len;
        while ((len = bf.read(chs))!= -1){
            bw.write(chs,0,len);
        }
        //释放资源
        bw.close();
        bf.close();
    }
}

字符缓冲流特有功能

  • BufferedWriter
    • void newLine()  写一行行分隔符。
  • BufferedReader
    • String readLine()读一行文字。结果包含内容的的字符串,不包括任何行终止字符,如果流的结尾已经到达,则为NULL
package IO;

import java.io.*;

public class IODemo14 {
    public static void main(String[] args) throws IOException {
/*        BufferedWriter bf = new BufferedWriter(new FileWriter("wuhu.java"));

        //写数据
        for (int i = 0; i < 10 ; i++) {
            bf.write("hello");
//            bf.write("\r\n");
            bf.newLine();
        }


        //释放资源
        bf.close();*/

        BufferedReader bf = new BufferedReader(new FileReader("wuhu.java"));

/*        String s = bf.readLine();
        System.out.println(s);

        s = bf.readLine();
        System.out.println(s);

        s = bf.readLine();
        System.out.println(s);


        s = bf.readLine();
        System.out.println(s);

        */

        String s;
        while ((s = bf.readLine())!=null){
            System.out.println(s);
        }
        bf.close();
    }
}

字符缓冲流复制Java文件特有功能改进版

 

package IO;

import java.io.*;

public class IODemo15 {
    public static void main(String[] args) throws IOException {
        //创建字符缓冲输入流对象
        BufferedReader br = new BufferedReader(new FileReader("E:\\IDEJAVA\\student\\src\\IO\\IODemo1.java"));
        BufferedWriter bw = new BufferedWriter(new FileWriter("wuhu.java"));


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

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

    }
}

IO流小结

 

 

 案例

  • 集合到文件
    • 需求:把ArrayList集合中的字符串数据写入到文本文件。要求:每一个字符串元素作为文件中的一行数据
    • 思路
      • 创建ArrayList集合
      • 往集合中存储字符串元素
      • 创建字符缓冲输出流对象
      • 遍历集合,得到每一个字符串数据
      • 调用字符缓冲输出流对象的方法写数据
      • 释放资源
package IO;

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

/*需求:把ArrayList集合中的字符串数据写入到文本文件。要求:每一个字符串元素作为文件中的一行数据
        思路
        创建ArrayList集合
        往集合中存储字符串元素
        创建字符缓冲输出流对象
        遍历集合,得到每一个字符串数据
        调用字符缓冲输出流对象的方法写数据
        释放资源*/
public class IODemo16 {
    public static void main(String[] args) throws IOException {
        ArrayList<String> array = new ArrayList<>();

        array.add("hello");
        array.add("world");
        array.add("java");


        BufferedWriter bf = new BufferedWriter(new FileWriter("array.txt"));


        for (String s : array) {
            bf.write(s);
            bf.newLine();
            bf.flush();

        }


        bf.close();
    }
}

案列

  • 文件到集合
package IO;

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

public class IODemo17 {
    public static void main(String[] args) throws IOException {
        BufferedReader bf = new BufferedReader(new FileReader("array.txt"));

        ArrayList<String> array = new ArrayList<>();

        String s ;
        while ((s = bf.readLine())!= null){
            array.add(s);
        }


        for (String s1 : array) {
            System.out.println(s1);
        }
    }
}

 

案例

  • 点名器
    • 需求:我有一个文件里面存储了班级同学的姓名,每一个姓名占一行,要求通过程序实现随机点名器
    • 思路:
      • 创建字符缓冲输入流对象
      • 创建ArrayList集合对象
      • 调用字符缓冲输入流对象的方法读数据
      • 把读取到的字符串数据存储到集合中
      • 释放资源
      • 使用Random产生一个随机数,随机数的范围在:[0,集合的长度]
      • 把上一步产生的随机数作为索引到ArrayList集合中获取值
      • 把上一步得到的值输出在控制台
package IO;

import java.io.*;
import java.lang.reflect.Array;
import java.util.ArrayList;
import java.util.Random;

/*
        需求:我有一个文件里面存储了班级同学的姓名,每一个姓名占一行,要求通过程序实现随机点名器
        思路:
            创建字符缓冲输入流对象
            创建ArrayList集合对象
            调用字符缓冲输入流对象的方法读数据
            把读取到的字符串数据存储到集合中
            释放资源
            使用Random产生一个随机数,随机数的范围在:[0,集合的长度]
            把上一步产生的随机数作为索引到ArrayList集合中获取值
            把上一步得到的值输出在控制台

*/
public class IODemo18 {
    public static void main(String[] args) throws IOException {
        BufferedReader br = new BufferedReader(new FileReader("array.txt"));
        ArrayList<String> array = new ArrayList<>();

        String len ;
        while ((len = br.readLine())!= null){
            array.add(len);
        }
        br.close();

        Random i = new Random();
        int i1 = i.nextInt(array.size());

        String s = array.get(i1);
        System.out.println(s);
    }
}
  • 集合到文件(改进版)
    • 需求:把ArrayList集合中的字符串数据写入到文本文件。要求:每一个字符串元素作为文件中的一行数据
    • 思路
      • 定义学生类
      • 创建ArrayList集合
      • 创建学生对象
      • 把学生对象添加到集合中
      • 创建字符缓冲输出流对象
      • 遍历集合,得到每一个字符串数据
      • 把学生对象的数据拼接成指定格式的字符串
      • 调用字符缓冲输出流对象的方法写数据
      • 释放资源
package IO;

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

/*需求:把ArrayList集合中的字符串数据写入到文本文件。要求:每一个字符串元素作为文件中的一行数据
        思路
        定义学生类
        创建ArrayList集合
        创建学生对象
        把学生对象添加到集合中
        创建字符缓冲输出流对象
        遍历集合,得到每一个字符串数据
        把学生对象的数据拼接成指定格式的字符串
        调用字符缓冲输出流对象的方法写数据
        释放资源*/
public class IODemo19 {
    public static void main(String[] args) throws IOException {
        ArrayList<Student> array = new ArrayList<>();

        Student s1 = new Student("shuja001", "钟启航", 21, "六安");
        Student s2 = new Student("shuja002", "孙多庆", 22, "合肥");
        Student s3 = new Student("shuja003", "方世涛", 23, "芜湖");
        Student s4 = new Student("shuja004", "张益磊", 20, "北京");
        Student s5 = new Student("shuja005", "刘占猛", 13, "南京");

        array.add(s1);
        array.add(s2);
        array.add(s3);
        array.add(s4);
        array.add(s5);

        BufferedWriter bw = new BufferedWriter(new FileWriter("array.txt"));

        for(Student s : array){
            StringBuffer sb = new StringBuffer();
            StringBuffer st = sb.append(s.getID()).append(s.getName()).append(s.getAge()).append(s.getAddress());

            bw.write(st.toString());
            bw.newLine();
            bw.flush();
        }

        bw.close();
    }
}

 

文件到集合(改进版)

  • 需求:
    • 把文本文件中的数据读取到集合中,并遍历集合
    • 要求:
      • 文件中每一行数据是一个学生对象的成员变量值
    • 思路:
      • 定义学生类
      • 创建字符缓冲输入流对象
      • 创建ArrayList集合对象
      • 调用字符缓冲输入流对象的方法读数据
      • 把读取到的字符串数据用split()进行分割,得到一个字符串数组
      • 创建学生对象
      • 把字符串数组中的每一个元素取出来对应的赋值给学生对象的成员变量值
      • 把学生对象添加到集合
      • 释放资源
      • 遍历集合
package IO;
/*
需求:
        把文本文件中的数据读取到集合中,并遍历集合
        要求:
        文件中每一行数据是一个学生对象的成员变量值
        思路:
        定义学生类
        创建字符缓冲输入流对象
        创建ArrayList集合对象
        调用字符缓冲输入流对象的方法读数据
        把读取到的字符串数据用split()进行分割,得到一个字符串数组
        创建学生对象
        把字符串数组中的每一个元素取出来对应的赋值给学生对象的成员变量值
        把学生对象添加到集合
        释放资源
        遍历集合
*/

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

public class IODemo20 {
    public static void main(String[] args) throws IOException {
        BufferedReader br = new BufferedReader(new FileReader("array.txt"));
        ArrayList<Student> array = new ArrayList<>();

        String len;
        while ((len = br.readLine())!=null){
            String[] sp = len.split(",");
            Integer i = Integer.valueOf(sp[2]);
            Student s1 = new Student(sp[0], sp[1], i, sp[3]);
            array.add(s1);
        }
        
        br.close();
        for (Student s : array){
//            StringBuffer sb = new StringBuffer();
//            sb = sb.append(s.getID()).append(",").append(s.getName()).append(",").append(s.getAge()).append(",").append(s.getAddress());
//            System.out.println(new String(sb));

            System.out.println(s.getID()+","+s.getName()+","+s.getAge()+","+s.getAddress());
        }
    }
}

 

学生信息排序录入

package com.shujia.java.day21;

import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;
import java.util.Comparator;
import java.util.Scanner;
import java.util.TreeSet;

/**
 *  键盘录入5个学生信息(姓名,语文成绩,数学成绩,英语成绩),按照总分从高到低存入文本文件
 */
public class StudentDemo1 {
    public static void main(String[] args) throws IOException {
        //创建集合对象
        TreeSet<Student> ts = new TreeSet<Student>(new Comparator<Student>() {
            @Override
            public int compare(Student o1, Student o2) {
                int i = o2.getScore() - o1.getScore();
                int i1 = i == 0 ?o1.getChinese() - o2.getChinese() : i;
                int i2 = i1 == 0 ?o1.getMath() - o2.getMath() : i1;
                int i3 = i2 == 0 ?o1.getEnglish() - o2.getEnglish() : i2;
                int i4 = i3 == 0?o1.getName().compareTo(o2.getName()) : i3;
                return i4;
            }
        });

        //创建Scanner对象
        Scanner sc = new Scanner(System.in);

        //键盘录入学生对象信息到集合
        for(int i =1;i<=5;i++){
            System.out.println("请录入第"+i+"个学生的信息");
            System.out.println("姓名:");
            String name = sc.next();
            System.out.println("语文成绩:");
            int chinese = sc.nextInt();
            System.out.println("数学成绩:");
            int math = sc.nextInt();
            System.out.println("英语成绩:");
            int english = sc.nextInt();

            //创建学生对象
            Student s = new Student(name, chinese, math, english);
            //把学生对象加到集合中
            ts.add(s);
        }

        //遍历集合,把数据写到文本文件中
        BufferedWriter bw = new BufferedWriter(new FileWriter("studentInfo.txt"));
        bw.write("学习信息如下:");
        bw.newLine();
        bw.flush();
        bw.write("姓名\t语文成绩\t数学成绩\t英语成绩");
        bw.newLine();
        bw.flush();
        for (Student s : ts){
            bw.write(s.getName()+"\t"+s.getChinese()+"\t"+s.getMath()+"\t"+s.getEnglish());
            bw.newLine();
            bw.flush();
        }

        bw.close();
        System.out.println("学生信息录入完毕!!");


    }
}

 

复制单级文件夹

  • 思路:
    • 创建数据目录File对象
    • 获取数据源目录File对象的名称
    • 创建目的地目录File对象
    • 判断目的地目录对应的File是否存在,如果不存在,就创建
    • 获取数据源目录下所有文件的File数组
    • 遍历File数组,得到每一个File对象,该File对象,其实就是数据源文件
    • 获取数据源文件File对象的名称
    • 创建目的地文件File对象
    • 复制文件
      • 由于文件不仅仅是文本文件,还有图片,视频等文件,所以采用字节流复制文件
package IO;

import java.io.*;

/*思路:
        创建数据目录File对象
        获取数据源目录File对象的名称
        创建目的地目录File对象
        判断目的地目录对应的File是否存在,如果不存在,就创建
        获取数据源目录下所有文件的File数组
        遍历File数组,得到每一个File对象,该File对象,其实就是数据源文件
        获取数据源文件File对象的名称
        创建目的地文件File对象
        复制文件
        由于文件不仅仅是文本文件,还有图片,视频等文件,所以采用字节流复制文件*/
public class IODemo21 {
    public static void main(String[] args) throws IOException {
        //创建数据目录File对象
        File srcFolder = new File("D:\\兰智视频\\JAVA\\第二十二天");

        //获取数据源目录File对象的名称
        String srcFolderName = srcFolder.getName();

        //创建目的地目录File对象
        File desFolder = new File("E:\\复制文件", srcFolderName);

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

        File[] files = srcFolder.listFiles();
        for (File srcfile : files){
            //获取数据源文件File对象的名称
            String srcfileName = srcfile.getName();

            File desFile = new File(desFolder, srcfileName);

//            复制文件
            copyFile(srcfile,desFile);
        }
    }

    private static void copyFile(File srcfile, File desFile) throws IOException {
        BufferedInputStream bis = new BufferedInputStream(new FileInputStream(srcfile));

        BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(desFile));

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

        bos.close();
        bis.close();
    }
}

 

复制多级文件夹

  • 创建数据源File对象
  • 创建目的地File对象
  • 写方法实现文件夹的复制,参数为数据源File对象和目的地File对象
  • 判断数据源File是否是目录’
    • 是:
      • A:在目的地下创建和数据源File名称一样的目录
      • B:获取数据源File下所有文件或者目录的File数组
      • C:遍历该File数组,得到每一个File对象
      • D:把该File作为数据源File对象,递归调用复制文件夹的方法
    • 不是:说明是文件,直接复制,用字节流
package IO;

import java.io.*;

/*创建数据源File对象
        创建目的地File对象
        写方法实现文件夹的复制,参数为数据源File对象和目的地File对象
        判断数据源File是否是目录’
        是:
        A:在目的地下创建和数据源File名称一样的目录
        B:获取数据源File下所有文件或者目录的File数组
        C:遍历该File数组,得到每一个File对象
        D:把该File作为数据源File对象,递归调用复制文件夹的方法
        不是:说明是文件,直接复制,用字节流*/
public class IODemo22 {

    private static void copyFile(File srcfile, File desFile) throws IOException {
        BufferedInputStream bis = new BufferedInputStream(new FileInputStream(srcfile));

        BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(desFile));

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

        bos.close();
        bis.close();
    }
    public static void main(String[] args) throws IOException {
        File srcFile = new File("D:\\兰智视频\\JAVA\\第二十二天");
        File desFile = new File("E:\\复制文件");

        //写方法实现文件夹的复制,参数为数据源File对象和目的地File对象
        copyFolder(srcFile,desFile);

    }
    //复制文件夹
    private static void copyFolder(File srcFile, File desFile) throws IOException {
//        判断数据源File是否是目录
        if(srcFile.isDirectory()){
//            在目的地下创建和数据源File名称一样的目录
            String srcFileName = srcFile.getName();
            File newFolder = new File(desFile,srcFileName);

            if(newFolder.exists()){
                newFolder.mkdir();
            }
//            B:获取数据源File下所有文件或者目录的File数组
            File[] fileArray = srcFile.listFiles();

            //C:遍历该File数组,得到每一个File对象
            for (File file :fileArray){
//            把该File作为数据源File对象,递归调用复制文件夹的方法
                copyFolder(file,newFolder);
            }
        }else {  
//            不是:说明是文件,直接复制,用字节流
            File newfile = new File(desFile,srcFile.getName());
            copyFile(srcFile,newfile);
            
        }
    }
}

 

  

posted @ 2021-08-14 20:15  钟心意  阅读(772)  评论(0)    收藏  举报