输入输出流

输入输出流(每日笔记)

本人初识java,如有错误或者不足,虚心求各位大神教导

此总结只限老师提到的知识点,当然还有其它的知识点, java的水不浅,需要慢慢的摸索

什么是输入流?什么是输出流?

输入流

简单的说 输入流 就是把文件读到内存。

输出流

输出流 就是把内存中存储流的生成文件。

例如:修改一图片 需要通过输入流把图片读到内存,相应的软件对图片进行处理。处理完以后。修改好的“图片”仅仅是在内存中。需要用输出流进行保存。生成新修改的图片。

  • java中什么是文件
    • 相关记录或放在一起的数据集合,文件夹和文件都属于文件
  • 文件储存在哪里
    • 磁盘
  • java程序如何访问文件属性?
    • JAVA IPI:java.io.File

File类

包:java.io

File对象的创建

File file = new File("d:\\HelloWorld.java")

File常用方法

  • mkdir():创建单层文件夹

    public boolean mkdir() 
    
  • mkdir():创建多层文件夹

    public boolean mkdirs() 
    
  • getName():获取文件名

    public String getName()
    
  • getAbsolutePath():获取指定文件的绝对路径

    public String getAbsolutePath()
    
  • getPath():获取指定文件的相对路径

    public String getPath()
    
  • delete():删除指定的文件

    public boolean delete()
    
  • createNewFile()创建一个新的文件

    public boolean createNewFile() throws IOException
    
  • list():获取指定file对象下的文件文件名存入String[]中

    public String[] list(FilenameFilter filter) 
    
  • listFile():获取指定file对象下的file对象

    public File[] listFiles() 
    //此方法重写toString方法
    
  • 等等一系列方法

示例:

查询指定路径文件夹内所有包含"1.txt"的文件路径,并记录总条数

public class FileTest {
    private static Integer count = 0;
    public static Integer getFilesPath(String fileName, String dirName) {
        File file = new File(dirName);
        //获取指定文件夹下所有文件并将指定文件夹下所有的文件遍历
        File[] files = file.listFiles();
        for (File file1 : files) {
            //判断是否是文件,如果是文件就输出路径,如果不是文件就继续遍历
            if (file1.isFile()) {
                if (file1.getName().equals(fileName)) {
                    System.out.println(file1.getAbsolutePath());
                    count++;
                }
            } else {
                //递归
                getFilesPath(fileName, file1.getAbsolutePath());
            }
        }
        return count;
    }
    public static void main(String[] args) {
        String fileName = "1.txt";
        String dirName = "E:\\upload";
        Integer files = FileTest01.getFilesPath(fileName, dirName);
        System.out.println(fileName+"文件在"+dirName+"中出现了" + files + "次");
    }
}

我们了解了File类,发现File类可以操作查看文件,但是怎么操作文件内容呢?

IO流

我们知道一个字节有8位(bit),那么一个文件在计算机中传输,是先将文件拆分成最小的单位然后进行传输,再重新拼装形成一个文件,就像一股水流一样,bit就相当于水分子,字节相当于水滴

在这里插入图片描述

分类

  • 字节流:是以8位的byte字节作为传输单元
    • 输入流:外部数据写入程序 以InputStream 为基类
    • 输出流:程序内部数据写入外部 以OutputStream为基类
  • 字符流:是以16位的Unicode码作为传输单元
    • 输入流:Reader为基类
    • 输出流:Writer为基类

字节流

FileInputStream
  • 包:java.io

  • 常用方法

    • read(byte byte):

      • 每次调用读取一个字节
      • 当从输入流中读取出数据,返回的是读取字节的字节数,当从输入流中没有读取字节数时则返回-1
      public int read(byte b[], int off, int len) throws IOException
      //b[]为缓冲区  off为开始索引  len为缓冲区大小
      
    • close()

      public void close() throws IOException
      
    • 等等方法

  • 示例:

    public static void main(String[] args)  {
            //创建流对象
            InputStream fileInputStream = null;
            try {
                fileInputStream = new FileInputStream("E:\\upload\\1.txt");
                //读取数据
                int read = fileInputStream.read();
                //将数据输出
                byte[] bytes = {(byte)read};
                System.out.println(new String(bytes));
                //这里直接catch一个大的Exception
            } catch (Exception e) {
                e.printStackTrace();
            }finally {
                //关闭资源
                if (fileInputStream!=null){
                    try {
                        fileInputStream.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            }
        }
    

    注意这里读取流的方式是一位一位读取的,如果文件庞大十分影响效率,所以这里我们引出了个思想:缓冲区

  • 缓冲区的作用:

    • 缓冲区就是存在于内存中的一个数组。对于输出流,输出的数据会先进入缓冲区,缓冲区满再自动刷新到硬盘的文件中,因为减少了内存和硬盘之间的读写次数,所以提高了效率。

在这里插入图片描述

  • 示例:将指定文件输出到控制台

    public class FileInputStreamTest01 {
        public static void main(String[] args)  {
            FileInputStream fis = null;
            try {
                //创建流对象
                fis = new FileInputStream("E:\\upload\\a.txt");
                //缓冲区
                byte[] bytes = new byte[1024];
                int len;
                while ((len=fis.read(bytes))!=-1){
                    //将内容流入缓冲区,并输出
                    fis.read(bytes,0,len);
                    System.out.println(new String(bytes));
                }
            } catch (Exception e) {
                e.printStackTrace();
            }finally {
                //关闭资源
                try {
                    if (fis!=null){
                        fis.close();
                    }
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
    }
    
    

注意使用完流对象,需要关闭流对象

FileOutputStream

包:java.io

了解过了FileInputStream输入流与缓冲区之后,输出流FileOutputStream与之相同

常用方法:

void write(byte[] b)
void write(byte[] b, int off, int len)
void write(int b) 
void close()

同样的OutputStream也有缓冲区

案例:复制文件

public class OutputStreamTest {
    public static void main(String[] args) {
        InputStream is = null;
        OutputStream os = null;
        try {
            //开启输入输出流
            is = new FileInputStream("E:/upload/img.png");
            os = new FileOutputStream("E:/upload/img/img.png");
            //缓冲区
            byte[] bytes = new byte[1024];
            int len = 0;
            while ((len = is.read()) != -1) {
                //将流中数据写入目的地
                os.write(bytes, 0, len);
            }
            //这里直接catch一个Excpetion(为了省事)
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            //关闭资源
            try {
                if (is != null) {
                    is.close();
                }
                if (os != null) {
                    os.close();
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

字符流

字符流:是以16位的Unicode码作为传输单元

Reader:

字符输入流的基类

常用子类:

BufferedReader

FilterReader

InputStreamReader

常用方法:

read()

close()

Writer

字符输入流的基类

常用子类:

BufferedWriter

FilterWriter

OutputStreamWriter

常用方法:

read()

close()

Reader与Writer的用法与字符流类似,也有缓冲区的思想,不同的是字节流的缓冲区是一个byte[]数组,字符流的缓冲区是一个char[]数组,如果流中内容有中文字符需要注意编码问题:

Reader的子类中有一个类:InputStreamReader我们看这个类的构造方法

InputStreamReader(InputStream in) 
InputStreamReader(InputStream in, Charset cs)
InputStreamReader(InputStream in, CharsetDecoder dec) 
InputStreamReader(InputStream in, String charsetName) 

我们可以使用

InputStreamReader(InputStream in, String charsetName) 

Writer的子类OutputStreamWriter与上面类似,都可以指定字符集

这里我为了书写方便异常我就直接throws了,大家不要学我

	public static void main(String[] args) throws IOException {
        InputStream is = new FileInputStream("E:\\upload\\a.txt");
        InputStreamReader isr = new InputStreamReader(is, "utf-8");

        OutputStream os = new FileOutputStream("E:\\upload\\file\\a.txt");
        OutputStreamWriter osw = new OutputStreamWriter(os, "utf-8");

        char[] chars = new char[1024];
        int len;
        while ((len = isr.read(chars)) != -1) {
            osw.write(chars, 0, len);
            osw.flush();
        }
        
        isr.close();
        is.close();
        osw.close();
        os.close();
    }

这里注意:编码问题遇到的问题有很多, 这里不做细讲

BufferedReader与BufferedWriter

为了提高字符流读写的效率,引入了缓冲机制,进行字符批量的读写,提高了单个字符读写的效率。BufferedReader用于加快读取字符的速度,BufferedWriter用于加快写入的速度

ReadLine()方法就是Read()方法的功能进行增强 可以读一行文字。

案例:

    public static void main(String[] args) throws IOException {
        FileReader reader = new FileReader("E:\\upload\\a.txt");
        BufferedReader br = new BufferedReader(reader);

        FileWriter writer = new FileWriter("E:\\upload\\file\\a.txt");
        BufferedWriter bw = new BufferedWriter(writer);

        String str;
        while ((str = br.readLine()) != null) {
            bw.write(str);
			bw.newLine();
        }
         bw.close();
         writer.close();
         reader.close();
         br.close();
    }

IO流使用规律总结:

  • 明确要操作的数据是数据源还是数据目的(要读还是要写)
    • 源文件:InputStream  Reader
    • 目的文件:OutputStream  Writer
  • 明确要操作的设备上的数据是字节还是文本
    • 源:
      • 字节:InputStream
      • 文本:Reader
    • 目的:
      • 字节:OutputStream
      • 文本:Writer
  • 明确是否需要额外功能?
    • 需要转换——转换流 InputStreamReader OutputStreamWriter
    • 需要高效——缓冲流Bufferedxxx
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值