RandomAccessFile文件合并

16 篇文章 0 订阅
3 篇文章 0 订阅

需求:承接前面的文章(小电影下载),这里补个文件合并的,以后自己也可以用O(∩_∩)O...

这里因为每个电影分块文件大小都是不固定的,所以没有使用多线程进行文件写入....

好了...直接上代码吧,需要的同学自己再封装一下了:

import java.io.*;
import java.util.ArrayList;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 *
 * 合并文件
 * @date 2019/9/15 15:04
 * @author wei.heng
 */
public class MergeFile {

	public static void main(String[] args) {

		String dir = "G:/haha/1_OM425NHJ";
		String suffix = ".ts";
		String fileSeperator = "/";
		List<File> files = getFiles(dir, suffix);
		// 按文件名排序
		reSortList(files);

		// 合并文件 - 文件名就取“1”了,合并后就排列在最前面嘛
		File newFile = new File(dir + fileSeperator + "1.ts");
		RandomAccessFile targetFile = null;
		long totalSize = 0;
		for (File file : files) {

			// 这里由于每个文件的大小都是不固定的,无法得知下一个文件写入的起始位置,只有用同步线程处理了
			FileInputStream fis = null;
			try {
				// 目标文件地址
				targetFile = new RandomAccessFile(newFile, "rw");
				// 移动到写入的节点
				targetFile.seek(totalSize);

				fis = new FileInputStream(file);
				byte[] bytes = new byte[1024*100];
				int r;
				while((r = fis.read(bytes)) != -1){
					targetFile.write(bytes, 0, r);
				}
				long fileSize = file.length();
				totalSize += fileSize;
			} catch (Exception e) {
				e.printStackTrace();
			} finally {
				if(fis != null){
					try {
						fis.close();
					} catch (IOException e) {
						e.printStackTrace();
					}
				}
			}
		}
		if(targetFile != null){
			try {
				targetFile.close();
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
	}

	/**
	 *
	 * 按文件末尾数字进行升序排列
	 * @param files 文件列表集合
	 * @date 2019/9/15 16:09
	 * @author wei.heng
	 */
	private static void reSortList(List<File> files) {
		files.sort((o1, o2) -> {
			String firstName = o1.getName();
			String secondName = o2.getName();
			// 正则匹配,获取文件末尾的数字
			String regex = "\\d+\\.ts";
			Pattern pattern = Pattern.compile(regex);

			Matcher m1 = pattern.matcher(firstName);
			Matcher m2 = pattern.matcher(secondName);

			if(m1.find() && m2.find()){
				String firstStr = m1.group();
				String secondStr = m2.group();
				if(firstStr != null && secondStr != null){
					int firstIndex = Integer.parseInt(firstStr.substring(0, firstStr.length() - 3));
					int secondIndex = Integer.parseInt(secondStr.substring(0, secondStr.length() - 3));
					if( firstIndex < secondIndex){
						return -1;
					} else if (firstIndex > secondIndex){
						return 1;
					}
				}
			}
			return 0;
		});
	}

	/**
	 *
	 * * 获取目录下的所有文件
	 * @param path 目录路径
	 * @param suffix 文件后缀
	 * @date 2019/9/15 15:05
	 * @author wei.heng
	 */
	private static List<File> getFiles(String path, String suffix){
		File root = new File(path);
		List<File> files = new ArrayList<>(0);
		if(!root.isDirectory()){
			if(root.getName().endsWith(suffix)){
				files.add(root);
			}
		}else{
			File[] subFiles = root.listFiles();
			assert subFiles != null;
			for(File f : subFiles){
				files.addAll(getFiles(f.getAbsolutePath(), suffix));
			}
		}
		return files;
	}
}

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值