Java多线程读取文件进行复制

本文介绍了一种使用Java多线程技术进行大文件读取和复制的方法。通过将文件分成多个部分,每个部分由一个独立的线程读取,最后将所有线程读取的数据合并,实现高效的大文件复制。此方法可以显著提高文件处理速度。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

首先,这是线程类的内容。

public class ThreadReadFile extends Thread {
    private File file; // 要读取的文件file
    private int start; // 开始的字节数
    private int end; // 结束的字节数
    private ArrayList<byte[]> list;// 读取到的字节数组存入list集合中

    public File getFile() {
        return file;
    }

    public void setFile(File file) {
        this.file = file;
    }

    public int getStart() {
        return start;
    }

    public void setStart(int start) {
        this.start = start;
    }

    public int getEnd() {
        return end;
    }

    public void setEnd(int end) {
        this.end = end;
    }

    public ArrayList<byte[]> getList() {
        return list;
    }

    public void setList(ArrayList<byte[]> list) {
        this.list = list;
    }

    // 这里就是要实现的构造方法
    public ThreadReadFile(int start, int end, File file) {
        this.start = start;
        this.end = end;
        this.file = file;
        this.list = new ArrayList<byte[]>();
    }

    @Override
    public void run() {
        FileInputStream fis = null;
        try {
            fis = new FileInputStream(file);
            byte[] result = new byte[1024];
            int num = end - start + 1; //获取要读取的总字节数
            fis.skip(start - 1);//跳过之前的字节量
            //读取byte数组,并且保存在Arraylist集合中
            //每次read后,都会减少总字节数的值,直到完全保存
            for (int n = 0; n <= num;) {
                if (num <= 1024) {
                    byte[] result2 = new byte[num];
                    fis.read(result2);
                    list.add(result2);
                    break;
                } else {
                    fis.read(result);
                    list.add(result);
                    //注意这里,需要想办法清空byte[]值,不然等再次read的话,在覆盖值的时候会出现无法覆盖的情况
                    //具体原因还在想,我是采用重新实例化一个对象给它
                    result = new byte[1024];
                    num -= 1024;
                }
            }
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try {
                //关闭输入流
                fis.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

接下来,用main方法实现多线程读取文件并进行写入复制

public class MainTest {
    public static void main(String[] args) throws IOException, InterruptedException { 
        // 这里是要读取的文件
        FileInputStream fis1 = new FileInputStream(file);
        // 这里是为了拿到文件的字节数。
        int num = fis1.available();
        fis1.close();
        // 把文件分为3个线程进行读取
        ThreadReadFile thread1 = new ThreadReadFile(1, num / 3, file);
        ThreadReadFile thread2 = new ThreadReadFile(num / 3 + 1, num / 3 * 2, file);
        ThreadReadFile thread3 = new ThreadReadFile(num / 3 * 2 + 1, num, file);
        // 启动3个线程
        thread1.start();
        thread2.start();
        thread3.start();
        // 在线程运行的同时建立FileOutputStream输出流等待存入文件
        // 这里是要复制的文件路径
        File file2 = new File("D:/copy/" + file.getName());
        file2.createNewFile();
        FileOutputStream fos = new FileOutputStream(file2);
        // 通过join方法可以让主线程在thread进行死亡后再执行list的赋值操作,以下3个线程同理
        thread1.join();
        thread2.join();
        thread3.join();
        ArrayList<byte[]> list = thread1.getList();
        list.addAll(thread2.getList());
        list.addAll(thread3.getList());
        // 文件存入
        for (byte[] value : list) {
            fos.write(value);
        }
        fos.flush();
        // 关闭输出流,程序结束
        fos.close();
    }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值