Featured image of post javaIO流

javaIO流

javaIO流

跟着https://drun1baby.github.io/2022/05/30/Java-IO%E6%B5%81/学习

创建文件

根据路径创建一个 File 对象

  • 方法 new File(String pathname)
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
package IOStream;

import java.io.File;
import java.io.IOException;

public class NewFile {
    public static void main(String[] args) {
        createFile();
    }
    public static void createFile() {
        File file = new File("D:\\idea\\javatest\\src\\IOStream\\1.txt");
        try{
            file.createNewFile();
            System.out.println("Create Successfully");
        }catch(IOException e){
            e.printStackTrace();
        }
    }
}

根据父目录 File 对象,在子路径创建一个文件

  • 方法 new File(File parent, String child)
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
package IOStream;
import java.io.File;
import java.io.IOException;
public class NewFile02 {
    public static void main(String[] args) {
        createFile();
    }
    public static void createFile() {
        File parentFile = new File("D:\\idea\\javatest\\src\\IOStream");
        File file = new File(parentFile, "2.txt");
        try{
            file.createNewFile();
            System.out.println("Create Successfully");
        }catch(IOException e){
            e.printStackTrace();
        }
    }
}

根据父目录路径,在子路径下生成文件

  • 方法 new File(String parent, String child)
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
package IOStream;
import java.io.File;
import java.io.IOException;

public class NewFile03 {
    public static void main(String[] args) {
        createFile();

    }
    public static void createFile() {
        String parentpath ="D:\\idea\\javatest\\src\\IOStream";
        String filename = "3.txt";
        File file = new File(parentpath,filename);
        try{
            file.createNewFile();
        }catch(IOException e){
            e.printStackTrace();
        }
    }
}

获取文件信息

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
package IOStream;
import java.io.File;

public class GetFile {
    public static void main(String[] args) {
        getFileContents();
    }
    public static void getFileContents() {
        File file = new File("D:\\idea\\javatest\\src\\IOStream\\3.txt");
        System.out.println("文件名称为:" + file.getName());
        System.out.println("文件的绝对路径为:" + file.getAbsolutePath());
        System.out.println("文件的父级目录为:" + file.getParent());
        System.out.println("文件的大小(字节)为:" + file.length());
        System.out.println("这是不是一个文件:" + file.isFile());
        System.out.println("这是不是一个目录:" + file.isDirectory());
    }
}

目录与文件操作

文件删除

  • 使用 file.delete(文件)
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
package IOStream;
import java.io.File;

public class FileDelete {
    public static void main(String[] args) {
        deleteFile();
    }
    public static void deleteFile() {
        File file = new File("D:\\idea\\javatest\\src\\IOStream\\3.txt");
        System.out.println(file.delete()?"Deleted Successfully":"Failed to Delete");
    }
}

目录删除

  • 方法 file.delete(目录),这里有个小坑,只有空的目录才可以删除,不然会显示删除失败。

示例跟上面一样

创建单级目录

  • 方法 file.mkdir()

创建多级目录

  • 方法 file.mkdirs()

文件流的一些操作

Runtime 命令执行操作的 Payload

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
package IOStream.RCETest;

import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;

public class RuntimeExec {
    public static void main(String[] args) throws IOException {
        InputStream in = Runtime.getRuntime().exec("whoami").getInputStream();
        byte[] buf = new byte[1024];
        ByteArrayOutputStream out = new ByteArrayOutputStream();
        int len=0;
        while ((len = in.read(buf))!=-1){
            out.write(buf, 0, len);
        }
        System.out.println(out.toString());

    }
}

byte用来缓存数据

FileInputStream

read()方法

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
read() 
	public int read(byte[] b) throws IOException {
        return read(b, 0, b.length);
    } 
	从此输入流中读取一个数据字节
	
	如果没有输入可用则此方法将阻塞 
	
	指定者  InputStream 中的 read 
	
	返回 下一个数据字节如果已到达文件末尾则返回 -1 
	
	抛出 IOException - 如果发生 I/O 错误

之前我们用 file 的一系列操作读取过文件的信息,现在我们用 FileInputStream.read() 来读取文件内容。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
package IOStream;

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

public class FileInputRead {
    public static void main(String[] args) {
        readFile();
    }
    public static void readFile(){
        String filepath="D:\\idea\\javatest\\src\\IOStream\\3.txt";
        FileInputStream fis=null;
        int length=0;
        try{
            fis=new FileInputStream(filepath);
            while ((length=fis.read())!=-1){
                System.out.print((char)length);
            }
        }catch (IOException e){
            e.printStackTrace();
        }finally {
            try{
                fis.close();
            }catch (IOException e){
                e.printStackTrace();
            }
        }
    }
}

read(byte[] d) 方法

允许在方法中添加一个字节数组。

当我们设置缓冲区的值为 8 时,若文件中的字符长度超过了 8,则会换行输出。

再回到之前我们讲的 Runtime 类进行命令执行的 Payload,在那里,我们设置的 Cache 缓冲区的值为 1024.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
package IOStream;

import java.io.FileInputStream;
import java.io.IOException;

public class FileInputRead02 {
    public static void main(String[] args) {
        readFile();
    }
    public static void readFile(){
        String filepath="D:\\idea\\javatest\\src\\IOStream\\3.txt";
        FileInputStream fis=null;
        byte[] buffer=new byte[8];//设置缓冲区,缓冲区大小为8字节
        int length=0;
        try{
            fis=new FileInputStream(filepath);
            while ((length=fis.read(buffer))!=-1){
                System.out.print(new String(buffer,0,length));
            }
        }catch (IOException e){
            e.printStackTrace();
        }finally {
            try{
                fis.close();
            }catch (IOException e){
                e.printStackTrace();
            }
        }
    }
}

FileOutputStream

往文件里面写数据

write(byte[] b) 方法

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
write(byte[] b)
public void write(byte[] b)
           throws IOException
 b.length 个字节从指定 byte 数组写入此文件输出流中
覆盖
 OutputStream 中的 write
参数
b - 数据
抛出
IOException - 如果发生 I/O 错误

尝试写内容到文件里

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
package IOStream;

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

public class FileOutputWrite {
    public static void main(String[] args) {
        writeFile();
    }
    public static void writeFile()  {
        String filePath = "D:\\idea\\javatest\\src\\IOStream\\1.txt";
        FileOutputStream fos = null;
        try {
            fos = new FileOutputStream(filePath);//注意fos的作用域,这里它需要在finally被捕获
            String content = "gulugulu";
            try{
                fos.write(content.getBytes());//String类型的字符串可以使用getBytes()方法将字符串转换为byte数组
            } catch (IOException e) {
                e.printStackTrace();
            }
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        }
        finally{
            try {
                fos.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

write(byte[] b, int off, int len) 方法

  • 将指定 byte 数组中从偏移量 off 开始的 len 个字节写入此文件输出流。
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
package IOStream;

import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.charset.StandardCharsets;

public class FileOutputWrite02 {
    public static void main(String[] args) {
        writeFile();
    }
    public static void writeFile(){
        String filePath = "D:\\idea\\javatest\\src\\IOStream\\1.txt";
        FileOutputStream fos = null;
        try{
            fos = new FileOutputStream(filePath);
            String content = "hajimi";
            try{
                fos.write(content.getBytes(StandardCharsets.UTF_8),0,6);
            } catch (IOException e) {
                e.printStackTrace();
            }
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        }
        finally{
            try {
                fos.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

追加写入

如果想要写入的数据不被覆盖,可以设置 FileOutputStream 的构造方法 append 参数设置为 true

1
2
3
fileOutputStream = new FileOutputStream(filePath);
// 设置追加写入
fileOutputStream = new FileOutputStream(filePath), true;

文件拷贝 —— input output 结合

利用前文讲的 fileInputStreamfileOutputStream 进行文件拷贝。

原理上来说,先将文件的内容(注意,其实图片当中也是内容,这个内容不光是文字!) 读取出来,再写入新的文件当中。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
package IOStream;

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

public class FileCopy {
    public static void main(String[] args) {
        copyFile();
    }
    public static void copyFile(){
        String originalPath = "D:\\idea\\javatest\\src\\IOStream\\1.txt";
        String endPath = "D:\\idea\\javatest\\src\\IOStream\\2.txt";
        FileInputStream fis = null;
        FileOutputStream fos = null;
        try{
            fis = new FileInputStream(originalPath);
            fos = new FileOutputStream(endPath);
            byte[] buffer = new byte[1024];
            int len = 0;
            while ((len = fis.read(buffer))!=-1) {
                fos.write(buffer,0,len);
            }
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try{
                fis.close();
                fos.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

FileReader

1
2
3
public class FileReader extends InputStreamReader
用来读取字符文件的便捷类此类的构造方法假定默认字符编码和默认字节缓冲区大小都是适当的要自己指定这些值可以先在 FileInputStream 上构造一个 InputStreamReader
FileReader 用于读取字符流要读取原始字节流请考虑使用 FileInputStream

读取文件内容

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
package IOStream;

import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;

public class FileReaderTest {
    public static void main(String[] args) {
        readFile();
    }
    public static void readFile(){
        String filePath = "D:\\idea\\javatest\\src\\IOStream\\1.txt";
        FileReader fis = null;
        try{
            fis = new FileReader(filePath);
            int len = 0;
            char[] buf = new char[1024];
            while ((len = fis.read(buf))!=-1){
                System.out.println(new String(buf,0,len));
            }
        } catch (IOException e) {
            e.printStackTrace();
        }finally {
            try{
                fis.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}
  • FileReader 将会一个一个字符读取,因此可以不乱码输出中文
Licensed under 9u_l3
使用 Hugo 构建
主题 StackJimmy 设计