java文件的操作笔记

2017-12-22 14:29:58

IO流
  1. 什么是流

    • 流是用于连接程序和设备之间的管道,主要用于数据传输。这个管道上有很多的按钮,每个近按钮可以实现不同的功能。
  2. 流的分类

    • 四大基本抽象流(输入流,输出流,字节流,字符流)
    • 文件流 缓冲流 转换流 数据流 Printi流 Object流
import java.io.FileReader;

public class Test1
{
    public static void main(String[] args) throws Exception
    {
        // read input是输入流 wirite output是输出流
        // read write是字符流 input output 是字节流
        FileReader wj = new FileReader("/home/nosay/Documents/work/java/aa.txt");

        int aa; //这里必须定义成整型,java规定read()函数的返回值是整型的
        aa = wj.read(); //读取一个字符

        System.out.println("文件的内容为:");

        while (aa != (-1))  //ASCII码是从0开始的数字,只有什么都没有时候才会返回-1
        {
            System.out.println((char)aa);
            aa = wj.read();
        }

        wj.close();

    }
}

运行结果为:

但是如果把字符流读取更换为字节流读取,也就是把

FileReader wj = new FileReader("/home/nosay/Documents/work/java/aa.txt");

换成

FileInputStream wj = new FileInputStream("/home/nosay/Documents/work/java/aa.txt");

执行以后发现,所有出现中文的地方,全部都变成乱码了,如图

这是因为1字符=2字节
所以字符流是两字节两字节取出的,而字节流是一个字节一个字节取出来的。
其中英文字母和数据占用的是一个字节,而我们的汉字是占用两个字节
所以一个汉字,如果取一半的话,肯定是显示的为乱码的。
所以如果文件中含有汉字的时候,就必须要使用字符流去读取的。

但是字节流是不是没有存在的必要了呢?下面来说一下字节流的优点

  • 字节流

看下面的代码

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

public class Test1
{
    public static void main(String[] args) throws Exception
    {

        FileReader fz = new FileReader("/home/nosay/1.png");
        FileWriter zt = new FileWriter("/home/nosay/2.png");
        
        int aa;
        aa = fz.read();
        
        while (aa != -1)
        {
            zt.write(aa);
            aa = fz.read();
        }
        zt.flush();
        fz.close();
        zt.close();
    }
}

执行的时候发现,新生成的图片是无法显示的,而换成字节流读取写入时,更改为如下代码

import java.io.FileInputStream;
import java.io.FileOutputStream;

public class Test1
{
    public static void main(String[] args) throws Exception
    {
        FileInputStream fz = new FileInputStream("/home/nosay/1.png");
        FileOutputStream zt = new FileOutputStream("/home/nosay/2.png");

        int aa;
        aa = fz.read();

        while (aa != -1)
        {
            zt.write(aa);
            aa = fz.read();
        }
        zt.flush();
        fz.close();
        zt.close();
    }
}

发现图片是要吧正常打开的,这是因为字符流复制的时候,是两个字节两个字节一起复制的,
而两个字符复制这些资源文件的时候,如图片,视屏,音乐等,编码是出问题的,这个了解一下就可以了。
所以说复制这些资源文件的时候,必须要用字节流,而复制文本文件的时候,必须要使用字符流,记住就可以了。

  • 缓冲流

上面代码中的zt.flush()是干嘛用的呢,它是将流中残留的内容全部输出
什么意思呢?
就比如我们拿吸管来喝饮料,当杯子里没有饮料的时候,不代理吸管中没有残留饮料了,从理论上来说,你的饮料并没有喝干净。在文件读取中,也是存在这样的一个管道,而flush()这个方法,就是把残留的东西全部输出,所以我们记住在文件关闭之前执行一次就可以了。
缓冲流救命代码

import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.FileInputStream;
import java.io.FileOutputStream;

public class Test1
{
    public static void main(String[] args) throws Exception
    {
        BufferedInputStream hcfz = new BufferedInputStream(new FileInputStream("/home/nosay/1.png"));
        BufferedOutputStream hczt = new BufferedOutputStream(new FileOutputStream("/home/nosay/2.png"));

        byte[] hc = new byte[2048]; //数字是缓冲区的大小,单位是字节
        int ff;

        ff = hcfz.read(hc);

        while (ff != (-1))
        {
            hczt.write(hc,0,ff); //为了防止最后一次写入数据,长度于缓冲区不同
            ff = hcfz.read(hc);
        }

        hczt.flush();
        hczt.close();
        hcfz.close();
    }
}
  • 数据流的传输
import java.io.*;

public class Test1
{
    public static void main(String[] args) throws Exception {

        ByteArrayOutputStream zjszl = new ByteArrayOutputStream();
        DataOutputStream sjl = new DataOutputStream(zjszl);
        long aa = 123456789;

        sjl.writeLong(aa);

        byte[] zjsz = zjszl.toByteArray();
        ByteArrayInputStream srl = new ByteArrayInputStream(zjsz);
        DataInputStream sjsr = new DataInputStream(srl);

        long ss;

        ss = sjsr.readLong();

        System.out.println(ss);

    }
}